2012-05-13 12 views
10

Ho alcune stringhe che sono circa 10K caratteri ciascuna. C'è molta ripetizione in loro. Sono oggetti JSON serializzati. Mi piacerebbe comprimerli facilmente in un array di byte e decomprimerli da un array di byte.Come posso facilmente comprimere e decomprimere le stringhe su/da matrici di byte?

Come posso fare più facilmente questo? Sto cercando i metodi in modo da poter effettuare le seguenti operazioni:

String original = "....long string here with 10K characters..."; 
byte[] compressed = StringCompressor.compress(original); 
String decompressed = StringCompressor.decompress(compressed); 
assert(original.equals(decompressed); 
+1

Vorrei utilizzare InflatorInputStream/DeflatorOutputStream con ByteArrayInput/OutputStream. –

+2

C'è una classe 'zip' facile da usare là fuori ... edit - è qui http://docs.oracle.com/javase/6/docs/api/java/util/zip/package-summary. html e sembra usare le classi @peter menzionate. –

+2

Che ne dici di questo? http://stackoverflow.com/questions/3649485/how-to-compress-a-string –

risposta

23

Si può provare

enum StringCompressor { 
    ; 
    public static byte[] compress(String text) { 
     ByteArrayOutputStream baos = new ByteArrayOutputStream(); 
     try { 
      OutputStream out = new DeflaterOutputStream(baos); 
      out.write(text.getBytes("UTF-8")); 
      out.close(); 
     } catch (IOException e) { 
      throw new AssertionError(e); 
     } 
     return baos.toByteArray(); 
    } 

    public static String decompress(byte[] bytes) { 
     InputStream in = new InflaterInputStream(new ByteArrayInputStream(bytes)); 
     ByteArrayOutputStream baos = new ByteArrayOutputStream(); 
     try { 
      byte[] buffer = new byte[8192]; 
      int len; 
      while((len = in.read(buffer))>0) 
       baos.write(buffer, 0, len); 
      return new String(baos.toByteArray(), "UTF-8"); 
     } catch (IOException e) { 
      throw new AssertionError(e); 
     } 
    } 
} 
+2

Ciao, perché usi 'enum' invece di' class' qui? E 'per dimostrare un punto? –

+6

Alcune persone preferiscono utilizzare le classi enum come metodo per implementare singleton o classi solo statiche. Consigliato da Joshua Bloch, scrittore di Effective Java. –

+0

Si dice che non sono permesse istanze di questa classe. –

2

risposta di Pietro Lawrey può essere migliorata un po 'utilizzando questo codice meno complessa per la funzione di decompressione

ByteArrayOutputStream baos = new ByteArrayOutputStream(); 
    try { 
     OutputStream out = new InflaterOutputStream(baos); 
     out.write(bytes); 
     out.close(); 
     return new String(baos.toByteArray(), "UTF-8"); 
    } catch (IOException e) { 
     throw new AssertionError(e); 
    } 
0

Ho creato una libreria per risolvere il problema della compressione di stringhe generiche (specialmente quelle corte). Prova a comprimere la stringa usando vari algoritmi (semplice utf-8, codifica a 5 bit per lettere latine, codifica di huffman, gzip per stringhe lunghe) e sceglie quella con il risultato più breve (nel peggiore dei casi, sceglierà l'utf- 8 codifica, in modo da non rischiare mai di perdere spazio).

Spero che possa essere utile, ecco il link https://github.com/lithedream/lithestring

EDIT: mi sono reso conto che le corde siano sempre "lungo", i miei valori di default delle biblioteche sul gzip per quelle dimensioni, temo che non posso fare di meglio per voi .

Problemi correlati