020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记

待字闺中开发了一门区块链方面的课程:《深入浅出ETH原理与智能合约开发》,马良老师讲授。此文集记录我的学习笔记。

课程共8节课。其中,前四课讲ETH原理,后四课讲智能合约。
第七课分为三部分:

  1. Solidity语法之多继承
  2. ERC20众筹实例之合约分析
  3. ERC20众筹实例之部署调试

这篇文章是第七课第一部分的学习笔记:Solidity语法之多继承。


在前面的课程中,分别讲解了 Solidity 语言的两个语法难点:数组和合约,这节课继续讲解另一个语法难点:多继承,并有两个代码示例辅助理解知识点。

1、多继承规则

1.1 多继承规则

020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记_第1张图片
多继承规则

多继承经常出现在面向对象的编程语言中。但往往有二义性,影响代码的可读性、可维护性。

在多继承中,有个经典的钻石问题。如图所示,B、C都是继承自A,D同时继承自B和C,D的test方法就会遇到问题。

Solidity 智能合约为了解决这个问题,使用了C3线性化(维基链接)。D继承B和C时,根据书写的顺序,有继承的先后,如图中虚线所示,按DCBA的顺序。

1.2 实例

example_4.sol

020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记_第2张图片
example_4.sol

代码中,super是指父类的意思。

  1. Run 页面,先选择 D 合约,Deploy 部署代码;
  2. 再点 test 接口,下方点 Debug ;
  3. 在第 31、48、66 行设置断点;
  4. 点击跳到下一个断点,执行到第 66 行;
  5. 点 step into 进入到内部,执行到 C 合约内部;
  6. 点击跳到下一个断点,执行到第 48 行;
  7. 点 step into 进入到内部,执行到 B 合约内部。注意,这里不是跳到A合约,而是B合约。
  8. 后续演示略。从B合约可以再进入A合约。

2、复杂类型

020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记_第3张图片
复杂类型

接下来是两个非常隐蔽的语法难点。

2.1 局部变量类型

一个函数里,局部变量的常规类型是 memory,而局部变量类型如果是复杂类型,则其缺省类型是这个复杂类型的指针。就是说,如果不显式地声明它是 memory 类型的话,它就是指向复杂类型的 storage 指针。注意这里,指针是指向 storage 的,而不是 memory 。

第二句如图。

所以,在使用时,为了避免二义性,要显式地声明变量的类型。

2.2 var 类型推导

第二个易错的错误是var类型推导。

如图举例,如果把 x 推导为 8 位无符号整型,范围是0~255,在循环函数中,永远执行不完所有的循环,这会引起死循环,直到消耗完 gas 。所以,要避免这类错误。

2.3 实例

example_5.sol


020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记_第4张图片
example_5.sol
  1. 把编译器版本设置为0.4.17,高版本的有点儿问题。
  2. 部署
  3. 点击 test_Local_Var 接口,再点击下面的Debug,在调试区可以看到state_A的长度为4,如图。


    020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记_第5张图片
    点击test_Local_Var
  4. 在第 31 行设置一个断点,执行到断点处。此时state_A的长度变为9999,如图。


    020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记_第6张图片
    执行x.a=9999后

    因为长度length就是存在起始的位置上,x.a=9999改变了这个值。因为指针缺省指向整个合约实例的存储类型状态变量的起始地址(见课件文字)。这里要特别注意!数组的长度本来应该是4,现在成了9999,这会浪费很多 gas 。

  5. 本例的第二个接口是 var 类型推导,前文已说明,如果用第 39 行代码,会是死循环;而用第 38 行代码,则是可以的。

小结一下,本文主要讲解了 solidity 语法难点中的多继承,并有两个代码示例辅助理解。


不足之处,请批评指正。

你可能感兴趣的:(020:Solidity语法之多继承|《ETH原理与智能合约开发》笔记)