零知识证明入门指南:发展历程、应用场景和基础原理解析
最近这段时间,零知识证明项目(ZKP)在区块链圈的热度是真高,尤其是在扩容和隐私保护这两块,几乎成了风暴中心。但ZKP这东西吧,数学味儿太重,让很多想深入研究的爱好者望而却步。所以,我们打算从最基础的开始,用几篇报告,把ZKP的理论和应用掰开揉碎了聊聊,也算是咱们团队内部思考的一个沉淀。这是系列的第一篇,先从历史、应用场景和几个基本原理说起。
一、零知识证明的历史
现代零知识证明体系的源头,可以追溯到1985年Goldwasser、Micali和Rackoff三位大神合作发表的一篇论文(江湖人称GMR85)。这篇论文的核心思想是:在一个需要K轮对话的交互系统里,到底要交换多少“知识”,才能证明一个证言是对的?如果能做到信息交换量为零,那这就是“零知识证明”。在这个模型里,证明者被假设拥有无限的资源,而验证者资源有限。不过,这种交互式系统有个天生缺陷——它的证明不是数学上铁板钉钉的,而是基于概率的,尽管出错的概率极小 (1/2^n)。
所以,交互式系统并不完美,只具备“近似完备性”。后来诞生的非交互式系统(NP)才算是补齐了这个短板,成为零知识证明系统里最理想的基石。
早年的零知识证明系统在效率和可用性上都差强人意,长年徘徊在理论层面。直到最近十年,随着密码学在加密世界成为显学,ZKP才真正走向台前,成了关键的技术方向。特别是,能搞出一个通用的、非交互的、证明体积又小的协议,成了最重要的研究目标之一。
说白了,零知识证明就是在三个方面做博弈:证明生成的速度、验证的速度,以及证明的大小。一个理想的协议,得是证明快、验证快、证明体积还小。
2010年,Groth的论文《Short Pairing-based Non-interactive Zero-Knowledge Arguments》堪称里程碑,为后来ZKP里最重要的zk-SNARK理论奠定了基础。而在应用层面,2015年Zcash使用的零知识证明系统,实现了对交易和金额的隐私保护,这是决定性的突破。再后来,zk-SNARK和智能合约结合,应用场景一下子就打开了。
这期间,几个重要的学术成果值得拿出来单讲:
- :把证明和验证的时间压缩到了可以实际应用的程度,也是Zcash早期使用的底层协议。
2013年,Pinocchio (PGHR13)
- :精简了证明的体积,同时大幅提升了验证效率。直到今天,它也是应用最广的ZK基础算法。
2016年,Groth16
- :提出了一种非常短的非交互式零知识证明,最大的优势是不需要可信设置。你猜怎么着?论文发出来才6个月,就被Monero用上了,简直是理论到应用的最快落地速度之一。
2017年,Bulletproofs (BBBPWM17)
- :提出了同样不需要可信设置的zk-STARK算法协议。这也是当前ZK领域另一个备受瞩目的方向,StarkWare这个重量级项目就是以此为基础诞生的。
2018年,zk-STARKs (BBHR18)
当然,后来出现的PLONK、Halo2等也是极其重要的进展,它们都在不同层面改进了zk-SNARK方案。
二、零知识证明的应用简述
零知识证明最广泛的两个应用场景,就是隐私保护和扩容。早期,随着Zcash、Monero等明星项目的推出,隐私交易一度风头无两。但说实话,市场对隐私交易的需求并没有想象中那么迫切,所以这类项目慢慢进入了二三线阵营(并没有消失)。反观扩容,随着2020年以太坊2.0(现更名为共识层)正式转向以Rollup为核心的技术路线,ZK一下子又重回聚光灯下,成为最亮的仔。
隐私交易:
Zcash应用zk-SNARKs的流程大致是这样的:

Source: Demystifying the Role of zk-SNARKs in Zcash
- :通过KeyGen函数生成用于加密证明多项式的证明密钥和验证密钥。
系统设置阶段
- :使用ECIES加密方法生成公钥和私钥。
CPA阶段
- :生成新币的数量、公共地址以及币的承诺。
铸币阶段
- :生成zk-SNARK证明,并将证明添加至转账交易账本中。
转移阶段
- :验证者验证铸币和转账的交易量是否匹配。
验证阶段
- :接收方收到币。如果想花这笔钱,就再次调用转移过程,生成新的zk-SNARK证明,重复4-6步,完成交易。
收款阶段
Zcash使用零知识证明还是有局限性的。它基于UTXO模型,所以只是“屏蔽”了部分交易信息,而不是完全隐匿。加上它本身是基于比特币架构的独立网络,很难跟其他应用结合。到2022年的数据显示,真正使用Shielding(隐私交易)功能的用户还不到10%,这说明隐私交易在应用层面并没有取得很成功的推广。
相比之下,Tornado Cash采用的是单一大混币池的方案,更加通用,而且基于以太坊这个久经考验的网络。从技术上看,它本质上就是用了zk-SNARK的混币池,可信设置基于Groth 16的论文。它能保证的特性包括:
- 只有存进去的币才能被提取。
- 同一个币不能被提取两次。
- 证明过程跟币的“作废通知”绑定,用相同证明但不同Nullifier的哈希值无法提币。
- 安全性高达126-bit,不会因为组合使用而降级。
Vitalik曾提过,跟扩容比,隐私相对来说更容易实现。如果连扩容协议都能跑通,那隐私基本上不会成为解决不了的难题。
扩容:
在zk-rollup生态里,有两个关键角色:Sequencer和Aggregator。Sequencer负责打包交易,而Aggregator则负责把大量交易合并成一个Rollup区块,并生成一个SNARK证明(或者基于其他算法的零知识证明)。这个证明会跟L1链上以前的状态进行比较,进而更新以太坊的Merkle树,计算出新的状态树。

Source: Polygon
ZK rollup 的优缺点
- :费用低,不像OP那样容易受经济攻击,无需为交易设置延迟等待,能保护隐私,并且能快速实现最终确定性。
优点
- :生成ZK证明需要极大的计算量;存在安全问题(SNARK需要可信设置);不抗量子攻击(STARK可以,但SNARK不行);交易顺序可能被篡改。
缺点

Source: 以太坊research
根据数据可用性和证明方法的不同,StarkWare给L2做了一张经典的分级图(Volition模式下,数据可用层可以在链上和链下自由选择):

Source: Starkware
目前市场上最具竞争力的ZK rollup项目包括:StarkWare的StarkNet、Matter Labs的zkSync、Aztec的Aztec Connect,以及Polygon的Hermez和Miden、Loopring、Scroll等。
大家的分歧点,基本都集中在SNARK(及其改进版)和STARK的技术路线选择,以及对EVM的支持方式(是兼容还是完全等同)。
- :开发了通用的SNARK协议——Plonk。正在运行的Aztec3可能会支持EVM,但隐私优先级高于EVM兼容。
Aztec
- :用的是zk-STARK,不需要可信设置。但目前不支持EVM,有自己的编译器和开发语言。
StarkNet
- :也用了Plonk,支持EVM。zkSync 2.0是EVM兼容的,有自己的zkEVM。
zkSync
- :一种EVM兼容的ZK rollup,团队也是以太坊基金会zkEVM项目的重要贡献者。
Scroll
说到EVM兼容性,这是个老生常谈的难题。ZK系统和EVM兼容一直让人头疼,项目方一般都得做个取舍。有些项目为了强化ZK能力,会选择在自己的系统里做一个虚拟机,并配有专门的ZK语言和编译器。但这会显著提高开发者的学习门槛,而且因为基本不开源,对用户来说就是个黑箱子。目前的行业共识是两条路:要么跟Solidity的操作码完全兼容,要么设计一种新的虚拟机,既对ZK友好,又能兼容Solidity。老实说,业界也没想到能融合得这么快。近一两年技术的快速迭代,已经把EVM的兼容性提升到了一个新高度,开发者甚至能做到一定程度的无缝迁移(从以太坊主链到ZK rollup)。这绝对是个振奋人心的进展,也将直接影响ZK开发工具的生态和整个行业的竞争格局。这个问题,我们会在后续的报告里再详细讨论。
三、ZK SNARK 实现的基本原理
回到源头,Goldwasser、Micali和Rackoff为零知识证明定义了三个核心性质:
- :任何一个拥有合理证据的声明,都能被验证者成功验证。
完整性
- :任何一个只有不合理证据的声明,都不应该被验证者通过。
可靠性
- :验证的过程不会泄露证据以外的任何信息。
零知识
要理解ZKP,我们从zk-SNARK入手是最合适的,因为目前区块链上绝大多数的应用都基于SNARK。先搞清楚它的定义。
zk-SNARK的全称是:zero-knowledge Succinct Non-interactive ARguments of Knowledge。
- :证明过程零知识,不暴露多余信息。
Zero Knowledge
- :验证体积小,简洁。
Succinct
- :非交互,证明者发个证明过去就行,不用来回对话。
Non-interactive
- :具备“计算可靠性”,意思是只有有限计算能力的证明者不能伪造证明,但具有无限计算能力的证明者理论上可以。这跟“证明”略有区别。
ARguments
- :证明者不可能在不知道有效信息(也就是证据Witness,比如哈希函数的输入,或者一条能确定Merkle树根节点的路径)的情况下,凭空构造出一组有效的参数和证明。
of Knowledge
Groth16这个zk-SNARK方案的证明原理,可以用下面这张图来概括:

Source: https://learnblockchain.cn/article/3220
其核心步骤包括:
- 将待证明的问题转化为一个算术电路。
- 将这个电路“拍平”,转换成R1CS(Rank-1 Constraint System)的形式。
- 再将R1CS转换成QAP(Quadratic Arithmetic Programs),也就是二次算术程序。
- 创建一个可信设置,生成随机参数,包括证明密钥(PK)和验证密钥(VK)。
- 最后,利用这些参数进行zk-SNARK证明的生成与验证。