雖然這篇函釋範例鄉民發文沒有被收入到精華區:在函釋範例這個話題中,我們另外找到其它相關的精選爆讚文章
在 函釋範例產品中有32篇Facebook貼文,粉絲數超過4,514的網紅數學老師張旭,也在其Facebook貼文中提到, 【處處極限不存在的函數】 . 我記得自己剛升大一在學習微積分的時候,教授問了一個問題,「有沒有哪一種實變數實值函數是任何一點的極限都不存在的」,那時候我想了很久,總是想不出來到底要怎麼設計,才有辦法完成教授的要求。那時候我一直想不透的癥結點是,如果要在任意點的極限都不存在的話,那可能要先解決一個...
同時也有185部Youtube影片,追蹤數超過3萬的網紅孫在陽,也在其Youtube影片中提到,Excel數據編輯與視覺化分析-以觀光統計資料為例,資料分析目的,瞭解資料轉置與樞紐的差別。轉置的使用時機,使用功能操作,不用寫複雜函數,相信人人都可以理解。 孫在陽老師主講,[email protected] 範例、講義下載:https://goo.gl/ytzRxT 00:0...
「函釋範例」的推薦目錄
函釋範例 在 電影神搜 AgentMovie Instagram 的最佳解答
2021-07-27 16:00:52
唸小學的小月和四歲的妹妹小梅,跟著爸爸搬到郊外的一間舊屋子,準備迎接即將出院的母親。在那個被人戲稱為「鬼屋」的新家裡,她們的生活有了許多有趣的新發現,包含會突然四散逃走的灰塵精靈,以及神祕的龍貓與貓巴士。 有一天,小梅和姊姊小月吵架後失蹤了,小月只能尋求龍貓的幫助,展開一場尋找妹妹的奇幻冒險......
函釋範例 在 沒力史翠普yucaio(拿起筆就能寫) Instagram 的最佳解答
2021-01-12 06:56:51
【沒力說書】沒力的閱讀法-2 總之先看一下目錄 #馬上掌握該書的主要內容 #預先挑選喜歡的主題&章節 #重點不是整本讀完,而是找到觸動你的部分 #理論可能很老套,範例才是真正重點 目錄是書的骨架,除了小說之外 大多數的書只要先看目錄 就可以掌握七成內容 不需要從頭開始讀 好的小說即便從中...
-
函釋範例 在 孫在陽 Youtube 的最佳解答
2021-06-01 02:24:12Excel數據編輯與視覺化分析-以觀光統計資料為例,資料分析目的,瞭解資料轉置與樞紐的差別。轉置的使用時機,使用功能操作,不用寫複雜函數,相信人人都可以理解。
孫在陽老師主講,[email protected]
範例、講義下載:https://goo.gl/ytzRxT
00:00:00 取得資料
00:10:00 資料轉置
00:45:00 分析 -
函釋範例 在 孫在陽 Youtube 的最佳解答
2021-05-28 15:51:24國立陽明交通大學-數據科學與雲端運算- Advanced visualization-機器學習
大數據利用時間的特性,以統計圖表呈現分析結果,以然成為一種企業尋找管理策略的方法。商業智慧的成功,當然也可以促成醫學智慧的成功。
孫在陽老師主講,[email protected]
範例、講義下載:https://goo.gl/ytzRxT
時間軸
00:00:00 E3下載範例
00:09:40 進階視覺化分析
01:28:00 機器學習-線性回歸做預測
01:40:00 機器學習-分群 -
函釋範例 在 孫在陽 Youtube 的最佳解答
2021-05-28 13:34:09國立陽明交通大學-數據科學與雲端運算- Advanced visualization-機器學習
大數據利用時間的特性,以統計圖表呈現分析結果,以然成為一種企業尋找管理策略的方法。商業智慧的成功,當然也可以促成醫學智慧的成功。
孫在陽老師主講,[email protected]
範例、講義下載:https://goo.gl/ytzRxT
時間軸
00:00 PPT簡報實務應用簡介
06:10 尋找證基會文件
14:00 開啟下載文件
16:30 傳送到 Power Point
27:35 設計標題投影片
00:41:19 微軟的簡報模板
00:45:40 瘋簡報的模板
01:05:00 時程模板應用
01:21:23 項目清單模板應用1
02:00:00 項目清單模板應用2
函釋範例 在 數學老師張旭 Facebook 的最讚貼文
【處處極限不存在的函數】
.
我記得自己剛升大一在學習微積分的時候,教授問了一個問題,「有沒有哪一種實變數實值函數是任何一點的極限都不存在的」,那時候我想了很久,總是想不出來到底要怎麼設計,才有辦法完成教授的要求。那時候我一直想不透的癥結點是,如果要在任意點的極限都不存在的話,那可能要先解決一個問題,那就是在設計了一個在某一點,例如說 a 點,極限不存在的函數以後,要如何改造這個函數,才有辦法讓 a 點「旁邊」的點其極限也不存在。
.
(接下來的內容,建議同學們可以拿支筆在紙上按照說明把函數畫出來)
.
舉例來說,如果我們設計了一個在 x = 0 這個點極限不存在的函數(例如設定這個函數在 x 小於 0 時其函數值均為 0;而當 x 大於 0 時其函數值均為 1),那麼要如何改造或調整這個函數,才有辦法讓這個函數在 x = 0 的「旁邊」的點其極限也不存在呢?針對這個例子而言,或許可以這樣做:先將這個函數在 x 大於 1 以後的函數值改成 0.5,那麼這個函數就會變成在 x = 0 和 x = 1 的時候極限都不存在,但因為 1 並非 0「旁邊」的數字,所以顯然還要再調整,於是我們再將 x 大於 0.5 以後的函數值都改成 0.5,那麼這個函數就會變成在 x = 0 和 x = 0.5 處其極限不存在,但同樣地,因為 0.5 並非 0「旁邊」的數字,所以我們繼續調整這個函數,下一步當然是將 x 大於 0.25 以後的函數值都改成 0.5,依此類推,再下一步就是將 x 大於 0.125 以後的函數值都改成 0.5,持續這樣的步驟,最終我們會得到一個當 x 小於 0 時其函數值為 0 而當 x 大於 0 其函數值為 0.5 的函數。這個函數當然仍然在 x = 0 的時候其極限不存在,但是原本在調整時的兩點極限不存在,卻因無限持續這樣的步驟,而變回了僅在 x = 0 極限不存在的狀態。這結果實在令人沮喪。
.
之所以會產生這樣的狀況,是因為持續了無限次將新增的極限不存在的點向 x = 0 處靠近的緣故。既然如此,那如果不要持續上面的步驟無限次呢?如果僅持續有限次的步驟,那麼在該次步驟的下一次,一定可以把 x = 0 右邊新增的極限不存在的點向 x = 0 再靠近一些,這個推論的結果就是,如果僅持續有限次上述的步驟,那麼就無法達成創造一個在 x = 0 的「旁邊」的極限不存在的點。結果,無論是有限次或無限次操作上述的步驟,最終都無法達成我們的目標。這真的真的非常令人沮喪,因為這意味著從一個點的極限不存在出發,去逐步改造出一個處處極限不存在的函數,方向很可能是錯誤的。
.
那麼,該怎麼辦呢?
.
面對這個問題,當時的我最終並沒有自己解出來,而是一個比過奧數的朋友在老師公布答案之前成功地解了出來,並告訴我他的想法。
.
他告訴我,既然從一個點的極限不存在開始是行不通的,那就一次就創造一大堆極限不存在的點吧!例如一開始的函數乾脆設定成這樣:當 x 介在 n 和 n + 1 之間且 n 為偶數時,將其函數值設定為 0,而其他地方則設定為 1。例如,當 x 介在 0 和 1 之間或介在 2 和 3 之間時,其函數值就是 0,而當 x 介在 1 和 2 之間或介在 99 和 100 之間時,其函數值就是 1。如此一來,我們就獲得了一個在每一個整數點其極限都不存在的函數。
.
以此為起點,比起我想的那個例子最初的樣子一次新增了無限多個極限不存在的點,似乎好像有了長遠的進步,但到此階段實際上並沒有解決我最一開始講的問題的癥結點,那就是如何在一個極限不存在的點的「旁邊」創造一個極限也不存在的點。
.
為了解決這個問題,我的朋友告訴我,下一步是在每一個「區間」裡進行調整。用例子來說明而剩下類推的話,大概是這樣操作:例如,在 0 和 1 之間,函數值原本都是 0,但接下來把這個區間切割成 10 等分,然後第 1、3、5、7、9 個區間(也就是在 x 介在 0 和 0.1、介在 0.2 和 0.3、介在 0.4 和 0.5、介在 0.6 和 0.7、介在 0.8 和 0.9 之間的這幾個區間),我們把函數值調整成 1,其餘的不動,那麼我們就可以得到一個,除了在所有整數點極限都不存在的函數以外,這個函數在 0.1、0.2、0.3、0.4、0.5、0.6、0.7、0.8、0.9 的極限也不存在。那如果是在原本函數值為 1 的區間,則在等分割成 10 個區間以後,將第 2、4、6、8、10 個區間的函數值調整成 0。若將上面這些動複製到其他區間的話,那麼在每一個整數區間(就是 n 到 n + 1 的區間)裡面,其十分位數的位置其極限都不存在。
.
接下來,再將函數值為 1 的區間等分割為 10 個區間,然後第 2、4、6、8、10 個區間其函數值都調整成 0,而函數值為 0 的區間一樣等分割為 10 個區間,但是是將第 1、3、5、7、9 個區間的函數值調整成 1,那麼,這個函數就變成了一個除了在所有整數點極限都不存在以外,但在每一個整數區間裡面其百分位數的位置極限都不存在的函數。
.
再接下來,繼續進行上面的動作,不斷地十等分分割之前產生的區間,並且適當地調整其函數值,使其在任一階段裡面都是前一個區間裡面的函數值是 0 且後一個區間裡面的函數值是 1 ,或前一個區間的函數值是 1 而後一個區間裡的函數值是 0 的狀態,持續無限次,最終就會得到一個在任一點其極限值都不存在的函數了。
.
要證明這個函數處處極限不存在有分簡單版和嚴格版,這邊我們先講簡單版,以後有機會再談嚴格版。對於這個函數而言,固定任何一點 a,其左極限只有兩種可能,0 或 1,但因為這個函數被分割地非常地密,而且連續幾個區間在任一階段裡面都是一下子 0 一下子 1 這樣變動,所以這個函數在 a 點的左極限不存在,因此這個函數在 a 點的極限並不存在。最後,因為 a 這個點是任意取的,所以我們可以說這個函數的極限值在任意點都不存在。
.
這個答案真的很猛,因為當時在班上只有我那位奧數的朋友給出了教授點頭的答案。
.
雖然當初他並沒有辦法清楚地講出左極限不存在的原因,也因為我們還沒學到極限的嚴格定義,所以沒辦法用嚴謹的敘述來證明這樣的函數確實處處極限不存在,但現在回想起來,那位奧數朋友還是很猛!因為他就好像那種天生的小說家一樣,信手拈來就寫出了一本傑出的小說,而我們凡人卻連寫一篇普通的文章都很成問題。
.
講到這裡,今天的故事似乎已經講完,但其實還沒,因為這樣聰明的人,並不會只出現我們班上甚至是這個時代而已。
.
關於「是否存在一個處處極限都不存在的函數」這個問題,其實在 19 世紀時,就有一位叫做 Dirichlet 的德國數學家,他所創造出來的一種函數(後來稱為 Dirichlet 函數),就是處處極限不存在的函數。這個函數的定義如下:當 x 為有理數時,其函數值是 1;當 x 不為有理數時,其函數值是 0。這樣的函數確實也處處極限不存在,也是我教授當時給同學們預設的答案。
.
在這邊我就不文字解釋為何 Dirichlet 函數處處極限不存在了,但我有拍一部影片來說明,如果你想繼續看下去,可以點開我貼在本篇文章留言處的這部影片,我有盡量簡單地解釋為何 Dirichlet 函數處處極限不存在。
.
雖然 Dirichlet 函數處處極限不存在,但其實當初 Dirichlet 所面對的問題,並非「是否存在處處極限不存在的函數」,而是「是否存在無法圖像化的函數」。在經過可能類似這篇文章最一開始的那些推敲以後,Dirichlet 創造了 Dirichlet 函數,而這個 Dirichlet 函數就是一個「客觀存在」但「無法圖像化」的函數。並且,除了無法圖像化以外,Dirichlet 函數在數學上也有著很重要的地位,因為他常常是一些直覺上無法察覺的現象的重要例子。例如我們直覺上都會認為只要函數有週期,那麼就會存在最小週期,但 Dirichlet 函數就是一個不具有最小週期的週期函數,因為任意有理數都是它的週期。
.
關於 Dirichlet 函數的性質我們就講到這邊,或許以後有機會可以專門寫一篇跟 Dirichlet 函數有關的文章,不過有很多性質都是需要具備更多數學知識以後才能介紹的,所以如果真的要寫的話,那可能就還要再等一陣子了。
.
最後,跟大家介紹一下我上面所提到的影片,那是我在 2020 年時所拍攝的一系列微積分教學影片的其中一集。該系列影片基本上有觀念講解、精選範例和補充教材,近期我會開始陸續上傳到這裡,但不是每一部影片都會寫文章來搭配,所以如果你想跟著我上傳的速度一部一部看,而且不漏掉系列裡每一部影片的話,可以關注我在西瓜視頻、騰訊視頻和優酷視頻的頻道;如果你想一次看完我全系列的影片的話,可以關注我在 YouTube、bilibili 或 Pornhub 上的頻道,上面已經上傳了張旭微積分全系列影片。另外這系列影片都有講義電子檔可以搭配使用,如果你想要取得該電子檔的話,請幫我按讚這篇文章和這個粉專、分享這篇文章,並幫我到我的臉書粉專評論處寫個評論,然後私訊我的臉書粉專,我的夥伴就會回覆你講義電子檔的連結。
.
感謝你的觀看,希望這篇文章對你有所幫助,有任何問題或想法也歡迎在下面留言告訴我。另外,本文章同步發佈於數學老師張旭的 YouTube 頻道社群、微博、今日頭條、Medium 和 HackMD,若你也有上面提到的那些帳號,歡迎按讚、分享和關注!
函釋範例 在 Taipei Ethereum Meetup Facebook 的最佳解答
📜 [專欄新文章] [zkp 讀書會] Cairo 語言介紹
✍️ NIC Lin
📥 歡迎投稿: https://medium.com/taipei-ethereum-meetup #徵技術分享文 #使用心得 #教學文 #medium
Cairo 是 STARK 證明系統的其中一個編程語言,讓開發者能透過 Cairo 來使用 STARK,撰寫效能更高的 Dapp
Photo by Simon Berger on Unsplash
Warning:本篇會保持在 high level 的介紹,實際深入的部分請見文內附上的文檔或是官方開發者文件
背景介紹
建構於密碼學的零知識證明能提供計算的隱私性,但同時在區塊鏈生態系也被用來提升 Scalability — 我可以用 10 秒的運算資源來驗證原本耗費 1000 秒運算資源的計算過程
如同更多人熟悉的 SNARK,STARK 也是一個零知識證明的證明系統,但當前的 STARK 著重的是在 Scalability ,而非大家比較習以為常零知識證明提供的隱私性特質
其實目前基於 SNARK 的 Rollup 項目,例如 zkSync、Loopring、Aztec、zkopru,除了 Aztec 外,其他都是利用 SNARK 來增加 Scalability — 這些 Rollup 上資料都還是公開、沒有隱私性的
StarkWare 是目前唯一基於 STARK 的開發團隊
STARK 要加上隱私保護不會太難,只是 StarkWare 還沒有把這項功能放在未來規劃中
Cairo 簡介
標榜為圖靈完備的零知識證明系統語言,Cairo 對原本熟悉 Solidity 的開發者來說還是會感到比較難上手和陌生的。再加上套件庫還不夠充足,目前支援的雜湊函式是 Pedersen,數位簽章演算法是 ECDSA(相對於 SNARK,EdDSA 的效能反而比較差所以沒有支援)。
但 Cairo 還在早期開發的階段,相信開發體驗會越來越好的。
另外需要注意的是作為一個證明系統,會有 Prover 和 Verifier 的角色。而 STARK 的 Verifier 是公開的,但 Prover 軟體預計會有 License 保護。Prover 一般情況下不得用於商業用途,除非將 proof 上傳至官方的 Verifier。
最後要提及的是,第一版的 Cairo 是設計來方便開發者將 Dapp 的運算遷移至鏈下。不同於 Rollup,這個鏈下只會有它自己一個 Dapp。這個 Dapp 的項目方自己維護自己 Dapp 的 state。( Rollup 則是 operator 維護所有 Dapp 的 state,Dapp 開發者不需自己操煩)
這可能有點難懂。如果你有在寫 Solidity,想像一下今天你在合約要用到合約裡宣告的 storage 變數時,你要自己提供 merkle proof 上來,證明這個storage 變數真的是這個值。這個就是開發者要自己維護 state 的意思。
而第二版的 Cairo 則是 StarkNet 裡使用的 Cairo(第一和第二版是不同編譯器),這版的 Cairo 就是作為 Dapp 在 Rollup 開發所使用 — 開發者可以在合約裡宣告變數,變數的值不需開發者維護,可以直接假設存在。
註1:StarkWare 不喜歡 Rollup 這個詞,他們覺得 Data Availability 的需求是一段光譜:不一定得要把 data 全都送上 L1,中間有其他方式可以做不同層級的 Data Availability。
註2:第一版和第二版實際上在官方版本裡是 0.0.1 及 0.0.2,在撰文當前最新版即是 0.0.2
官方網站:https://www.cairo-lang.org
開發者文件:https://www.cairo-lang.org/docs/
開發環境
Cairo 有提供像是 Remix 的瀏覽器 IDE:playground。裡面提供各種範例練習和挑戰,除了可以編譯,還可以直接生成並上傳 proof。
註:但有些功能還是沒辦法在 playground 裡使用,例如要給你的程式 custom input 時。這時候只能在本地端開發才能使用這個功能。
開發 Cairo 要先安裝python,我將開發者文件整理出來的資料統整在這個 hackmd 文檔裡:https://hackmd.io/w690dpAQTsKeKZv3oikzTQ
裡面包含簡介、設置本地開發環境以及 Cairo 基礎(因為篇幅原因,所以不將內容複製到這裡)
註:我把開發者文件裡的代碼整理到這裡:https://github.com/NIC619/cairo_practice/tree/master/practices
如果不想在研究開發者文件過程中,還要自己手動拼湊裡面例子的話,可以直接用整理好的代碼來執行。同時 repo 裡還有包含一些額外自己測試 Cairo 功能的範例。
深入 Cairo
在那份 hackmd 文檔裡的開頭,可以連結到第二部分 — 深入 Cairo 的部分。裡面也是從開發者文件裡擷取出來我覺得比較重要的部分。如果你要讀開發者文件的話,我建議從 Hello Cairo 開始,它會從例子切入,會比較好知道 Cairo 怎麼使用。接著如果要更深入了解,再去讀 How Cairo Works。
StarkNet Cairo
第二版的 Cairo 其實功能和第一版的 Cairo 是差不多的,所以不必擔心在開發者文件裡學到的 Cairo 在 StarkNet 版本會不能用或差很多。在讀完 Hello Cairo/How Cairo works 後,就可以接著看 Hello StarkNet。會很順利的切換到 StarkNet 版本的 Cairo。
註1:我整理的文檔裡是按照第一版 Cairo 所寫的
註2:如果你從開發者文件一路看下來,體驗過非 StarkNet 版的 Cairo,那你在體驗 StarkNet 版的 Cairo 時一定會發現這更像一般智能合約的使用方式 — 你可以用 view 函式查詢 storage 變數,可以用 external 函式去執行合約(非 StarkNet 版本不是這樣操作 Dapp 的,這邊因為篇幅原因沒有詳細介紹)。
非常建議嘗試兩種版本的 Cairo,你會知道 1. 操作一個單獨在 L2 的 Dapp 和2. 操作與其他 Dapp 共存在 Rollup 上的 Dapp 的不同。這對了解 L2 怎麼運行、需要哪些資料、為什麼需要這些資料非常有幫助。
0.0.2 版的 StarkNet Cairo 目前還缺少一些功能:
函式還沒辦法宣告陣列或 struct 型態的參數
合約和合約之間還沒辦法互動
L1 沒有辦法讀取到 L2 的資料,L2 也沒辦法讀取到 L1 的資料。如果要建立跨 L2 Bridge,這個功能非常重要。
補充及個人心得
STARK 的 proof size 相比於 SNARK 系列的 proof size 大很多,又其證明所包含的交易數量對 proof size 和驗證時間的影響不大,所以把很多筆交易一併做一個 proof 會是對 STARK 非常有利、節省成本的方式(SNARK、STARK 比較表)。但這同時也是一個缺點,如果你的 Dapp 或 Rollup 的 TPS 不高,那就只能等更久時間搜集多一點的交易,要不然就只能提高成本來維持驗證 proof 的頻率。
StarkWare和 zkSync 一樣都有 Rollup 宇宙的概念( Rollup 宇宙的用詞並不精確,因為在他們的宇宙中不會所有子鏈都是 Rollup,而是會有依照 Data Availability 程度不同所區分的子鏈,像是 Validium、zk Porter 的設計),個人覺得能夠有(針對 Data Availability 程度的)選擇是會比只有一個選擇(完全 Data Available) 還好的方式,但實際上的可行性就要等其團隊釋出更多的資訊。
在 Rollup 越趨成熟的情況下,能夠提供快速跨 Rollup 服務的流動性提供者的角色會越來越重要。zk Rollup(StarkNet、zkSync、etc…)比 Optimistic Rollup (Optimism、Arbitrum、etc…)有著短上許多的 finalize 時間,這對降低流動性提供者的風險有很大的幫助,但目前 zk Rollup 支援合約功能甚至 L1 <-> L2 互動的完成度都比 Optimistic Rollup 還低上許多。短期內快速跨 Rollup 的服務應該還是侷限在 Optimitic Rollup 之間。
abbrev
[zkp 讀書會] Cairo 語言介紹 was originally published in Taipei Ethereum Meetup on Medium, where people are continuing the conversation by highlighting and responding to this story.
👏 歡迎轉載分享鼓掌
函釋範例 在 Taipei Ethereum Meetup Facebook 的精選貼文
📜 [專欄新文章] ZKP 與智能合約的開發入門
✍️ Johnson
📥 歡迎投稿: https://medium.com/taipei-ethereum-meetup #徵技術分享文 #使用心得 #教學文 #medium
這篇文章將以程式碼範例,說明 Zero Knowledge Proofs 與智能合約的結合,能夠為以太坊的生態系帶來什麼創新的應用。
本文為 Tornado Cash 研究系列的 Part 2,本系列以 tornado-core 為教材,學習開發 ZKP 的應用,另兩篇為:
Part 1:Merkle Tree in JavaScript
Part 3:Tornado Cash 實例解析
Special thanks to C.C. Liang for review and enlightenment.
近十年來最強大的密碼學科技可能就是零知識證明,或稱 zk-SNARKs (zero knowledge succinct arguments of knowledge)。
zk-SNARKs 可以將某個能得出特定結果 (output) 的計算過程 (computation),產出一個證明,而儘管計算過程可能非常耗時,這個證明卻可以快速的被驗證。
此外,零知識證明的額外特色是:你可以在不告訴對方輸入值 (input) 的情況下,證明你確實經過了某個計算過程並得到了結果。
上述來自 Vitalik’s An approximate introduction to how zk-SNARKs are possible 文章的首段,該文說是給具有 “medium level” 數學程度的人解釋 zk-SNARKs 的運作原理。(可惜我還是看不懂 QQ)
本文則是從零知識證明 (ZKP) 應用開發的角度,結合電路 (circuit) 與智能合約的程式碼來說明 ZKP 可以為既有的以太坊智能合約帶來什麼創新的突破。
基本上可以謹記兩點 ZKP 帶來的效果:
1. 擴容:鏈下計算的功能。
2. 隱私:隱藏秘密的功能。
WithoutZK.sol
首先,讓我們先來看一段沒有任何 ZKP 的智能合約:
這份合約的主軸在 process(),我們向它輸入一個秘密值 secret,經過一段計算過程後會與 answer 比對,如果驗證成功就會改寫變數 greeting 為 “answer to the ultimate question of life, the universe, and everything”。
Computation
而計算過程是一個簡單的函式:f(x) = x**2 + 6。
我們可以輕易推出秘密就是 42。
這個計算過程有很多可能的輸入值 (input) 與輸出值 (output):
f(2) = 10
f(3) = 15
f(4) = 22
…
但是能通過驗證的只有當輸出值和我們存放在合約的資料 answer 一樣時,才會驗證成功,並執行 process 的動作。
可以看到有一個 calculate 函式,說明這份合約在鏈上進行的計算,以及 process 需要輸入參數 _secret,而我們知道合約上所有交易都是公開的,所以這個 _secret 可以輕易在 etherscan 上被看到。
從這個簡單的合約中我們看到 ZKP 可以解決的兩個痛點:鏈下計算與隱藏秘密。
Circuits
接下來我們就改寫這份合約,加入 ZKP 的電路語言 circom,使用者就能用他的 secret 在鏈下進行計算後產生一個 proof,這 proof 就不會揭露有關 secret 的資訊,同時證明了當 secret 丟入 f(x) = x**2 + 6 的計算過程後會得出 1770 的結果 (output),把這個 proof 丟入 process 的參數中,經過 Verifier 的驗證即可執行 process 的內容。
有關電路 circuits 的環境配置,可以參考 ZKP Hello World,這裡我們就先跳過去,直接來看 circom 的程式碼:
template Square() { signal input in; signal output out; out <== in * in;}template Add() { signal input in; signal output out; out <== in + 6;}template Calculator() { signal private input secret; signal output out; component square = Square(); component add = Add(); square.in <== secret; add.in <== square.out; out <== add.out;}component main = Calculator();
這段就是 f(x) = x**2 + 6 在 circom 上的寫法,可能需要時間去感受一下。
ZK.sol
circom 寫好後,可以產生一個 Verifier.sol 的合約,這個合約會有一個函式 verifyProof,於是我們把上方的合約改寫成使用 ZKP 的樣子:
我們可以發現 ZK 合約少了 calculate 函式,顯然 f(x) = x**2 + 6 已經被我們寫到電路上了。
snarkjs
產生證明的程式碼以 javascript 寫成如下:
let { proof, publicSignals } = await groth16.fullProve(input, wasmPath, zkeyPath);
於是提交 proof 給合約,完成驗證,達到所謂鏈下計算的功能。
最後讓我們完整看一段 javascript 的單元測試,使用 snarkjs 來產生證明,對合約的 process 進行測試:
對合約來說, secret = 42 是完全不知情的,因此隱藏了秘密。
publicSignals
之前不太清楚 publicSignals 的用意,因此在這裡特別說明一下。
基本上在產生證明的同時,也會隨帶產生這個 circom 所有的 public 值,也就是 publicSignals,如下:
let { proof, publicSignals } = await groth16.fullProve(input, wasmPath, zkeyPath);
在我們的例子中 publicSignals 只有一個,就是 1770。
而 verifyProof 要輸入的參數除了 proof 之外,也要填入 public 值,簡單來說會是:
const isValid = verifyProof(proof, publicSignals);
問題來了,我們在設計應用邏輯時,當使用者要提交參數進行驗證的時候,publicSignals 會是由「使用者」填入嗎?或者是說,儘管是使用者填入,那它需不需要先經過檢查,才可以填入 verifyProof?
關鍵在於我們的合約上存有一筆資料:answer = 1770
回頭看合約上的 process 在進行 verifyProof 之前,必須要檢查 isAnswer(publicSignals[0]):
想想要是沒有檢查 isAnswer,這份合約會發生什麼事情?
我們的應用邏輯就會變得毫無意義,因為少了要驗證的答案,就只是完成計算 f(42) = 1770,那麼不論是 f(1) = 7 或 f(2) = 10,使用者都可以自己產生證明與結果,自己把 proof 和 publicSignals 填入 verifyProof 的參數中,都會通過驗證。
至此可以看出,ZKP 只有把「計算過程」抽離到鏈下的電路,計算後的結果仍需要與鏈上既有的資料進行比對與確認後,才能算是有效的應用 ZKP。
應用邏輯的開發
本文主要談到的是 zk-SNARKs 上層應用邏輯的開發,關於 ZKP 的底層邏輯如上述使用的 groth16 或其他如 plonk 是本文打算忽略掉的部分。
從上述的例子可以看到,即使我們努力用 circom 實作藏住 secret,但由於計算過程太過簡單,只有 f(x) = x**2+6,輕易就能從 answer 反推出我們的 secret 是 42,因此在應用邏輯的開發上,也必須注意 circom 的設計可能出了問題,導致私密訊息容易外洩,那儘管使用再強的 ZKP 底層邏輯,在應用邏輯上有漏洞,也沒辦法達到隱藏秘密的效果。
此外,在看 circom 的程式碼時,可以關注最後一個 template 的 private 與 public 值分別是什麼。以本文的 Calculator 為例,private 值有 secret,public 值有 out。
另外補充:
如果有個 signal input 但它不是 private input,就會被歸類為 public。
一個 circuit 至少會有一個 public,因為計算過程一定會有一個結果。
最後,在開發的過程中我會用 javascript 先實作計算過程,也可以順便產出 input.json,然後再用 circom 語言把計算過程實現,產生 proof 和 public 後,再去對照所有 public 值和 private 值,確認是不是符合電路計算後所要的結果,也就是比較 javascript 算出來的和 circom 算出來的一不一樣,如果不一樣就能確定程式碼是有 bug 的。
參考範例:https://github.com/chnejohnson/circom-playground
總結
本文的程式碼展現 ZKP 可以做到鏈下計算與隱藏秘密的功能,在真實專案中,可想而知電路的計算過程不會這麼單純。
會出現在真實專案中的計算像是 hash function,複雜一點會加入 Merkle Tree,或是電子簽章 EdDSA,於是就能產生更完整的應用如 Layer 2 擴容方案之一的 ZK Rollup,或是做到匿名交易的 Tornado Cash。
本文原始碼:https://github.com/chnejohnson/mini-zkp
下篇文章就來分享 Tornado Cash 是如何利用 ZKP 達成匿名交易的!
參考資料
概念介紹
Cryptography Playground
zk-SNARKs-Explainer
神奇的零知識證明!既能保守秘密,又讓別人信你!
認識零知識證明 — COSCUP 2019 | Youtube
應用零知識證明 — COSCUP 2020 | Youtube
ZK Rollup
動手實做零知識 — circom — Kimi
ZK-Rollup 开发经验分享 Part I — Fluidex
ZkRollup Tutorial
ZK Rollup & Optimistic Rollup — Kimi Wu | Medium
Circom
circom/TUTORIAL.md at master · iden3/circom · GitHub
ZKP Hello World
其他
深入瞭解 zk-SNARKs
瞭解神秘的 ZK-STARKs
zk-SNARKs和zk-STARKs解釋 | Binance Academy
[ZKP 讀書會] MACI
Semaphore
Zero-knowledge Virtual Machines, the Polaris License, and Vendor Lock-in | by Koh Wei Jie
Introduction & Evolution of ZK Ecosystem — YouTube
The Limitations of Privacy — Barry Whitehat — YouTube
Introduction to Zero Knowledge Proofs — Elena Nadolinski
ZKP 與智能合約的開發入門 was originally published in Taipei Ethereum Meetup on Medium, where people are continuing the conversation by highlighting and responding to this story.
👏 歡迎轉載分享鼓掌