ZIP으로 묶으면 얼마나 줄어들까?
직접 만든 반복 텍스트와 PNG·JPG 시험 화면을 같은 ZIP 설정으로 압축했습니다. 실제 용량 차이와 원본 복원 결과를 비교하고 파일·재현 코드를 공개합니다.
같은 ZIP 설정이어도 파일마다 줄어드는 정도가 달랐습니다
ZIP은 파일을 묶어 담는 형식입니다. 이번에 사용한 DEFLATE 압축은 반복되는 데이터 등을 더 짧게 표현하므로, 파일 안에 어떤 내용이 들어 있는지에 따라 결과가 달라집니다. PNG처럼 이미 압축을 사용하는 형식도 있어 확장자만으로 절약할 용량을 정하기는 어렵습니다.
직접 만든 반복 텍스트와 기존 실험의 PNG·JPG 시험 화면을 각각 ZIP으로 묶었습니다. 이미지를 다시 저장하거나 픽셀을 바꾸지 않고, 같은 압축 설정으로 실제 파일 크기와 복원 결과를 비교했습니다.
텍스트는 크게 줄었고, JPG도 약 3분의 1 줄었습니다
번호만 달라지는 가상 작업 기록 1,000행은 ZIP으로 묶자 원본의 약 7.8% 크기만 남았습니다. 같은 글자·도형 화면을 담은 PNG와 JPG는 서로 다른 감소 폭을 보였습니다.
| 시험 파일 | 원본 | ZIP | 감소율 | 직접 비교하기 |
|---|---|---|---|---|
| 반복 텍스트 1,000행 | 33,073바이트 | 2,581바이트 | 92.2% | 원본 받기 ZIP 받기 |
| PNG 시험 화면 | 57,368바이트 | 53,498바이트 | 6.7% | 원본 받기 ZIP 받기 |
| JPG 시험 화면 | 87,456바이트 | 59,095바이트 | 32.4% | 원본 받기 ZIP 받기 |
이번 PNG는 이미지를 한 번 더 압축했을 때 용량이 6.7% 줄었습니다. 반면 JPG는 32.4% 줄어, “JPG는 ZIP으로 묶어도 거의 줄지 않는다”는 설명이 이 파일에는 맞지 않았습니다.
텍스트는 같은 문구가 반복되도록 만든 자료이고, 두 이미지는 사진 없이 글자·표·도형을 배치한 한 화면입니다. 이 결과를 일반 문서나 사진 전체의 압축률로 해석할 수는 없습니다.
측정 . 감소율은 원본과 ZIP 전체 바이트 수의 차이를 원본 크기로 나눈 값입니다. ZIP의 파일명·헤더도 크기에 포함했습니다.
용량이 줄어도, ZIP을 풀면 원본 파일 그대로입니다
세 ZIP을 다시 열어 압축 전 파일과 비교했습니다. 모두 바이트 단위로 같았고 SHA-256 해시도 일치했으며, ZIP 내부의 CRC 검사도 통과했습니다. JPG를 ZIP으로 묶고 푸는 과정에서 화질이 더 낮아진 것은 아닙니다.
다만 이번 JPG가 PNG 원본과 같아졌다는 뜻은 아닙니다. ZIP을 풀면 압축하기 직전의 JPG가 그대로 돌아옵니다. 이미 JPG로 저장하면서 생긴 차이는 앞선 캡처 압축 실험에서 확인할 수 있습니다.
이번 결과에서 용량 절약이 가장 컸던 것은 반복 텍스트였습니다. 실제로 보낼 파일도 ZIP 전체 크기를 원본과 비교하면 얼마나 줄었는지 알 수 있습니다. 작은 파일은 파일명과 헤더가 더해져 오히려 커질 수 있으며, 이 실험에서는 작은 파일의 손익분기점까지 측정하지 않았습니다.
실험 조건과 재현 자료
Python 3.12.14의 표준 라이브러리와 zlib 1.3.2을 사용했습니다. DEFLATE 압축 수준은 6으로 고정했고, 각 ZIP에는 파일 하나만 넣었습니다. 처리 시간·암호화·여러 파일을 함께 묶는 경우나 다른 압축 프로그램은 비교하지 않았습니다.
같은 파일로 재현하는 방법
- 아래의 재현 코드와 위 표의 PNG·JPG 원본을 같은 폴더에 받습니다. 파일 이름은
reproduce.py,original.png,jpeg-q75.jpg로 유지합니다. 코드는 원본 이미지의 SHA-256을 대조하고 다른 파일이면 실행을 중단합니다. - Python이 설치된 환경에서
python reproduce.py를 실행합니다. 외부 패키지 없이 반복 텍스트와 ZIP 세 개, 측정 JSON, 비교 차트를 새reproduced폴더에 저장합니다. python reproduce.py --check를 실행하면 저장된 결과와 재생성한 ZIP이 바이트까지 같은지, 압축 해제 후 원본과 같은지 다시 검사합니다. 이 검사에서는 파일을 쓰지 않습니다.
텍스트는 UTF-8·BOM 없음·LF 줄바꿈을 사용한 가상 기록입니다. 두 줄의 제목·열 이름 뒤에 0001,문서,자료 정리,완료부터 번호가 1000인 행까지 생성합니다. 실제 업무나 이용자의 기록은 포함하지 않았습니다.
재현 시 ZIP 바이트가 달라지지 않도록 내부 파일 시각은 1980년 1월 1일, 권한은 100644로 고정하고 추가 필드와 주석은 비웠습니다. 이 내부 시각은 실험일이 아닙니다. 다른 Python·zlib 버전, 압축 수준이나 메타데이터를 쓰면 ZIP 크기와 해시가 달라질 수 있습니다.