Piotr Nowicki

Piotr Nowicki JFB Systems,
właściciel

Temat: pakowanie do zip bez kompresji

Próbuje zapisać kilka plików do zipa, zależy mi na szybkości więc chciałbym ustawić brak kompresji.

Napisałem kod:

public static void zipPackege(final String dirName){

final String nazwaPliku = "c:\\paczka.zip";
int x;
try{

final File katalog = new File(dirName);
final String[] nazwyPlikow = katalog.list();

final ZipOutputStream zos = new ZipOutputStream(
new BufferedOutputStream(
new FileOutputStream(nazwaPliku)));
zos.setMethod(ZipOutputStream.STORED);
for (int i = 0; i < nazwyPlikow.length; i++) {
System.out.println("Zapisywanie " + nazwyPlikow[i]);
final BufferedInputStream in = new BufferedInputStream(new FileInputStream(dirName
+"/"+nazwyPlikow[i]));
final ZipEntry entry = new ZipEntry(nazwyPlikow[i]);
entry.setMethod(ZipEntry.STORED);
zos.putNextEntry(entry);
while ( (x = in.read()) != -1 ) {
zos.write(x);
}
in.close();
}
zos.close();
} catch (final IOException ioe){
ioe.printStackTrace();
}
}


i dostaje wyjątek:
java.util.zip.ZipException: STORED entry missing size, compressed size, or crc-32
at java.util.zip.ZipOutputStream.putNextEntry(ZipOutputStream.java:167)
at Utils.zipPackege(Utils.java:85)
at Test.main(Test.java:25)

Ktoś wie o co chodzi? Albo jak to zrobić?

konto usunięte

Temat: pakowanie do zip bez kompresji

działający kod:

public class ZipTest {
private static long doChecksum(String fileName) {

CheckedInputStream cis = null;
try {
// Computer CRC32 checksum
cis = new CheckedInputStream(new FileInputStream(fileName),
new CRC32());

} catch (FileNotFoundException e) {
System.err.println("File not found.");
System.exit(1);
}

byte[] buf = new byte[128];
try {
while (cis.read(buf) >= 0)
;
} catch (IOException e) {
throw new RuntimeException("error while reading file", e);
}

long checksum = cis.getChecksum().getValue();
return checksum;

}

public static void zipPackege(final String dirName) throws IOException,
FileNotFoundException {

final String nazwaPliku = "c:\\paczka.zip";
int x;
final File katalog = new File(dirName);
final String[] nazwyPlikow = katalog.list();
final ZipOutputStream zos = new ZipOutputStream(
new BufferedOutputStream(new FileOutputStream(nazwaPliku)));
zos.setMethod(ZipOutputStream.STORED);

for (int i = 0; i < nazwyPlikow.length; i++) {
System.out.println("Zapisywanie " + nazwyPlikow[i]);

String filePath = dirName + "/" + nazwyPlikow[i];
final BufferedInputStream in = new BufferedInputStream(
new FileInputStream(filePath));
final ZipEntry entry = new ZipEntry(nazwyPlikow[i]);

entry.setMethod(ZipEntry.STORED);
entry.setSize(new File(filePath).length());
entry.setCrc(doChecksum(filePath));

zos.putNextEntry(entry);

while ((x = in.read()) != -1) {
zos.write(x);
}

in.close();
}
zos.close();
}

public static void main(String[] args) {
try {
zipPackege(new String("c:\\testZip\\"));
System.out.println("finished OK");
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}

}


odpowiedź była zawarta w komunikacie z wyjątku. ZipPart w przypadku metody store wymaga podania rozmiaru pliku i CRC.Dariusz Wawer edytował(a) ten post dnia 25.01.11 o godzinie 14:10
Piotr Nowicki

Piotr Nowicki JFB Systems,
właściciel

Temat: pakowanie do zip bez kompresji

Dzięki, przetestowałem i działa.

Byłem już blisko trochę innego rozwiązania, ale dostawałem:

Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
at java.util.Arrays.copyOf(Arrays.java:2786)
at java.io.ByteArrayOutputStream.write(ByteArrayOutputStream.java:94)
at com.google.common.io.ByteStreams.copy(ByteStreams.java:171)
at com.google.common.io.ByteStreams.toByteArray(ByteStreams.java:210)
at Utils.zipPackege(Utils.java:85)
at Test.main(Test.java:25)

jak chciałem stworzyć tablicę bajtów ze strumienia dla pliku ważącego ponad 1GB. Nawet po zwiększeniu pamięci dla Eclipse. Na mniejszych plikach nawet działało. Napisałem ku przestrodze, nie róbcie tak :-)

konto usunięte

Temat: pakowanie do zip bez kompresji

To teraz jeszcze jedno: kopiowanie danych po jednym bajcie jest raczej kiepskim i powolnym pomysłem. Wykorzystaj tablicę byte[] o jakiejś sensownej wielkości (np. o rozmiarze klastra na Twoim dysku) i przy jej pomocy wczytuj i zapisuj dane.



Wyślij zaproszenie do