在文件傳輸、網絡通訊場景中,壓縮能顯著降低帶寬佔用與延遲。Java java.util.zip 包提供 Deflater(壓縮)與 Inflater(解壓)類,實現標準 DEFLATE 算法(LZ77 + Huffman 編碼)。
| 類 | 關鍵方法 | 說明 |
|---|---|---|
| Deflater | setInput(byte[]), finish(), deflate(byte[]), end() | 壓縮輸入數據,finish() 表示輸入結束 |
| Inflater | setInput(byte[]), inflate(byte[]), finished(), end() | 解壓數據,finished() 判斷是否完成 |
import java.io.*;
import java.util.zip.*;
public class DeflateUtils {
/** 壓縮字節數組 */
public static byte[] compress(byte[] input) throws IOException {
try (ByteArrayOutputStream bos = new ByteArrayOutputStream()) {
Deflater deflater = new Deflater();
deflater.setInput(input);
deflater.finish();
byte[] buffer = new byte[1024];
while (!deflater.finished()) {
int len = deflater.deflate(buffer);
if (len > 0) bos.write(buffer, 0, len);
}
deflater.end();
return bos.toByteArray();
}
}
/** 解壓字節數組 */
public static byte[] decompress(byte[] input) throws IOException {
try (ByteArrayOutputStream bos = new ByteArrayOutputStream()) {
Inflater inflater = new Inflater();
inflater.setInput(input);
byte[] buffer = new byte[1024];
while (!inflater.finished()) {
int len = inflater.inflate(buffer);
if (len <= 0) break;
bos.write(buffer, 0, len);
}
inflater.end();
return bos.toByteArray();
}
}
/** 文件壓縮示例:讀取文件 → 壓縮 → Base64 編碼 → 解碼 → 解壓 → 寫入文件 */
public static void main(String[] args) {
try {
// 1. 讀取原文件
byte[] original = readFile("D:\\testdeflate.txt");
// 2. 壓縮
byte[] compressed = compress(original);
// 3. Base64 編碼(便於網絡傳輸/文本存儲)
String encoded = Base64.getEncoder().encodeToString(compressed);
// 4. 模擬傳輸後解碼
byte[] decoded = Base64.getDecoder().decode(encoded);
// 5. 解壓
byte[] decompressed = decompress(decoded);
// 6. 寫入驗證文件
writeFile("D:\\testinflate.txt", decompressed);
System.out.println("原始大小: " + original.length);
System.out.println("壓縮後: " + compressed.length);
System.out.println("壓縮率: " + String.format("%.2f%%", (1 - (double) compressed.length / original.length) * 100));
System.out.println("驗證 " + (java.util.Arrays.equals(original, decompressed) ? "通過" : "失敗"));
} catch (Exception e) {
e.printStackTrace();
}
}
private static byte[] readFile(String path) throws IOException {
try (FileInputStream fis = new FileInputStream(path)) {
byte[] buf = new byte[fis.available()];
fis.read(buf);
return buf;
}
}
private static void writeFile(String path, byte[] data) throws IOException {
try (FileOutputStream fos = new FileOutputStream(path)) {
fos.write(data);
}
}
}
ByteArrayOutputStream 累積輸出,避免一次性分配大數組導致 OOM。finish() 告知壓縮器輸入結束,繼續調用 deflate() 直到 finished() 返回 true;end() 釋放本地資源。若需標準 .gz 或 .zip 文件格式,直接使用 GZIPOutputStream、ZipOutputStream,它們內部同樣基於 Deflater 實現,但添加了文件頭、校驗和元數據。
DeflaterOutputStream 包裝輸出流,簡化代碼。new Deflater(Deflater.BEST_COMPRESSION) 或 BEST_SPEED,平衡 CPU 與體積。掌握 Deflate 核心 API,能靈活應對各類壓縮需求,從 RPC 參數壓縮到日誌存儲優化均得心應手。