⚙️ 第六章 自己动手压缩数据
📄 一句话概括

无损是把重复的规律记账省下来,账还在、随时能还原;有损是把看不出来的部分真的扔掉,账撕了、回不来。

📝 本节和前面几节的关系

6.6 把无损压缩压到了极限,这一节说清两类压缩的分界,也是本章的收口。

一、无损:账还在

无损压缩的做法是找出数据里的重复与规律,用更紧凑的方式记账。 记账并没有丢信息——所以随时能照账还原,一个字节都不差。 实测:27 个字节的数据压到 6 个,再解回来,与原文完全一致。 无损的典型场合:文本、程序、压缩包、数据库备份——这些东西差一个字节都可能出大事。

二、有损:账撕了

有损压缩干脆把一部分信息真的丢掉——赌的是【这点差别没人看得出来】。 实测:把每个字节的低 3 位丢掉(模拟量化),1024 个字节里有 896 个被改动(87.5%),最大误差 7。 因为是扔而不是记账,所以不可能还原。 换来的好处也很明确:压缩比比无损大得多,几十倍、上百倍都有可能。

三、各自靠什么、用在哪

无损靠规律:重复、频率、上下文——凡是数据里有规律的地方都能下手。 有损靠感知:人眼对亮度敏感对色度迟钝、人耳对某些频率不敏感——专挑感知不到的地方扔。 无损用在哪:文本、程序、代码、压缩包、医疗影像、法律文档。 有损用在哪:图片、音频、视频——只要最终是给人看的,就有商量的余地。

四、怎么选,一句话

问自己一个问题:这份数据将来要不要被精确还原? 要——只能用无损,压不动也得认。 不要——优先有损,能省的空间大得多。 所以同一个系统里两类常常并存:日志和配置用无损,封面图和视频用有损。 这也回过头点亮了整章的主线:压缩不是魔法,只是把数据里的规律换成更短的写法。

五、动手 Demo:无损压缩与有损压缩

无损是记账省下的,随时能还原;有损是真的把看不出来的部分扔掉。 拿数据实测一遍就明白了。

src = b"A" * 10 + b"B" * 5 + b"C" * 12
enc = b"".join(bytes([v, k]) for v, k in
               ((0x41, 10), (0x42, 5), (0x43, 12)))
back = b"".join(bytes([enc[i]]) * enc[i + 1]
                for i in range(0, len(enc), 2))
print("无损还原一致吗:", back == src)
raw = bytes(range(256)) * 4
lossy = bytes(x & 0xF8 for x in raw)
print("有损改动了", sum(1 for a, b in zip(raw, lossy) if a != b), "个字节")

实跑输出:

--------------------------------------------------------------------
无损压缩与有损压缩
--------------------------------------------------------------------

  对比项             无损压缩                 有损压缩
  -----------------------------------------------------------------
  能不能原样还原     能,一个字节都不差       不能,只能差不多
  压缩比             通常两到五倍             可以到几十上百倍
  靠什么             找数据里的重复与规律     丢掉人感觉不到的部分
  典型场合           文本、程序、压缩包       图片、音频、视频

  拿数据实测一遍。先看无损:

    原始          27 字节
    压缩后        6 字节
    还原回来      完全一致

  再看有损——**把每个字节的低 3 位直接丢掉**(模拟量化):

    原始字节数    1024
    被改动的字节  896(87.5%)
    最大误差      7(低 3 位最大就是 7)
    能原样还原吗  不能——信息已经真丢了

  一句话分清两者:
    **无损压缩是把【重复的规律】记账省下来,账还在,随时能还原。**
    **有损压缩是把【看不出来的部分】真的扔掉,账撕了,再也回不来。**

无损往返上完全一致;有损改动后1024 个字节中 896 个变了(87.5%)、最大误差 7。 无损的账还在,有损的账撕了——这就是两类压缩的分界线。

30 秒实验

  1. 把一张 jpg 图片反复保存几十次,看画质会不会越来越差,为什么。
  2. 想想 zip 和 mp4 分别属于哪一类,能不能把 mp4 再无损压一半。

常见误区

  1. 以为无损压缩只是【质量更好】。它是能精确还原,不是好一点。
  2. 以为有损可以反复压缩。每压一次就丢一层,越压越糊。
自测三问(点开对答案) 1. 无损和有损的分界线是什么? —— 能不能一个字节都不差地还原——无损能,有损不能。 2. 两类压缩各自靠什么? —— 无损靠数据里的重复与规律;有损靠人的感知盲区,丢掉感觉不到的部分。 3. 怎么决定该用哪一类? —— 问这份数据将来要不要被精确还原:要就只能无损,不要就优先有损。

相关笔记