關(guān)于payable關(guān)鍵字用于修飾地址變量的解釋
????當(dāng)payable用于修飾函數(shù),它有明確的作用和語義,被修飾的函數(shù)在被調(diào)用時(被調(diào)用解析邏輯中的過濾器攔截成功),如果value不為空并且該函數(shù)是payble則會執(zhí)行轉(zhuǎn)賬和函數(shù)調(diào)用邏輯。這個作用是實質(zhì)性的。
????但是作為轉(zhuǎn)賬發(fā)起方,它現(xiàn)在要向某個地址發(fā)起轉(zhuǎn)賬,收款方是否能夠接收這筆轉(zhuǎn)賬,取決于收款方的合約邏輯安排,這個邏輯安排對轉(zhuǎn)賬發(fā)起方是未知的,現(xiàn)在它用payable修飾這個地址,只是表達(dá)一種“希望這個地址能夠接收我的轉(zhuǎn)賬”這樣一種意圖而已,這種意圖用在參數(shù)傳遞的場景下有微弱的意義:告訴調(diào)用者,我會用這個地址發(fā)起轉(zhuǎn)賬,希望你能保證對方有收款的能力。這就是payble的作用。但幾乎沒有用。收款邏輯安排很復(fù)雜,是一個過濾器鏈條,發(fā)起方不同的轉(zhuǎn)賬方式會導(dǎo)致轉(zhuǎn)賬成功失敗的不同結(jié)果,函數(shù)通過將地址參數(shù)修飾為payble是希望調(diào)用者提供某種保障,但調(diào)用者并不具備足夠信息。是否成功,跟你自己的轉(zhuǎn)賬方式還有關(guān)系。所以這種契約關(guān)系中的責(zé)任分配就更加費解。
????如果把payble語義限定一下:它聲明被調(diào)用合約有能力接收calldata為空這種方式的轉(zhuǎn)賬調(diào)用,似乎語義能夠略清晰一些,它在要求address這個合約安排了receive()函數(shù),或者payble的fallback。但也只是略清晰而已,對于形成有約束力的契約關(guān)系不具備值得考慮的作用。
? ?當(dāng)使用call函數(shù)來轉(zhuǎn)賬時,payble修飾符已經(jīng)不需要,這個事實也反映出solidity語言設(shè)計者的意圖;當(dāng)初安排address的payble修飾符,應(yīng)該就是因為send和transfer而設(shè)的,也就是針對calldata為空的調(diào)用而言的,也就是在聲明這個address的合約有receive()或者payable的fallback。但如上所言,這并沒有什么卵用。
? ? 所以是垃圾設(shè)計安排。但也情有可原,歷史問題。
????另外關(guān)于send和transfer也不要去記。比如同to.send(uamount)只是call{value:amount, gas:2300}("")而已。send講call的success返回值直接返回,transfer判斷success,success為false時進(jìn)行revert。這樣理解一下就夠了。收款方并不知道你是call還是send還是transfer,沒有區(qū)別。