以太坊solidity学习记录(五)函数入门

个人目录

以太坊solidity学习记录(一)新版在线remix编译器的使用(2020.4.27)
以太坊solidity学习记录(二)基础操作整理
以太坊solidity学习记录(三)基础数据操作
以太坊solidity学习记录(四)地址与交易
以太坊solidity学习记录(五)函数入门
以太坊solidity学习记录(六)内存与结构体

1.函数重载

结论:
1.函数重载是指函数命名相同,但需要满足以下两个条件之一
a.函数传入参数类型不同
b.函数传入参数数量不同
2.如果函数多个参数都匹配,那么会报错
3.address因为实际存储的也是uint160
代码

pragma solidity ^0.4.0;


contract funtest{
    
    
    /*function fun0() {
        
    }
    
    
    function fun0() {
        
    }*/
      uint public test= 0;
      
    function fun1(uint num1,uint num2) {
        test = 10;
    }
    
    
    function fun1(uint num1) {
        test = 20;
    }
    
    
    function fun2(uint a) {
        test = 100;
    }
    
    
    function fun2(string a) {
         test = 200;
    }
    
    
    
    function fun3(address a) {
        test=1000;
    }
    
    
    function fun3(uint160 a){
        test=2000;
    }
    
    
    
    
    function fun4(uint8 a){
         test=10000;
    }
    
    
    function fun4(uint16 a){
        test=20000;
    }
    
    
    
    
    function fun1test() public view returns(uint){
        fun1(1,2);
        return test;
    }
    
     function fun2test() public view returns(uint){
        fun2('asdasd');
        return test;
    }
    
    function fun3test() public view returns(uint){
        fun3(0x2e805eC48BdFBc458e7446058F94a315896A1cF6);
        //仅使用address类型,可以运行并运行address参数的重载函数
        return test;
    }
    
    //function fun3test2() public view returns(uint160){
        //uint160  如果转化成uint160类型并运行,那么报错          
        //temp=uint160(0x2e805eC48BdFBc458e7446058F94a315896A1cF6);
        //fun3(temp);
        //return temp;
    //}
    
    
    
    
    function fun4test() public view returns(uint){
        fun4(256);
        return test;
    }
   
    
    function reset() public{
        test = 0;
    }
    

}

运行结果
在这里插入图片描述

2.函数传入参数

结论:
1.可以直接对传入参数里面的命名来进行对应命名。这样可以调整顺序
2.格式
函数名({类型1:value1,类型2:value2,…,类型n:valuen})需要打{},而且等号(=)换成冒号(:)
3.使用时必须传入所有参数,否则报错

contract nametest{
    
    uint public num;
    string public teststring;
    
    function setvalue(uint num1,string teststring1){
        num=num1;
        teststring = teststring1;
    }
    
    function test1(){
        setvalue(1,'a');
    }
    
    function test2(){
        setvalue({num1:1,teststring1:'a'});
    }
    
    function test3(){
        setvalue({teststring1:'a',num1:1});
    }
    
    //function wrongtest4(){
    //    setvalue({teststring1:'a'});
    //}
    
}

运行结果:
其他的可以自行点击test1,test2,test3看结果
在这里插入图片描述

3.函数返回参数

结论:
1.solidity可以有多个返回值,可以命名(类型1 value1,类型2 value2,....,类型n valuen),可以直接赋值,如value1=111;,赋值之后return里面对应参数也会修改,可以不用return。
2.return语句后面可以接表达式,如uint类型 return (value1+value2, value1*value2);
3.可以直接接具体数值,如uint类型 return (1+2,1*2,'teststring');

代码

contract returntest{
    function test1() public view returns(uint8 num1,uint8 num2,string teststring){
        num1=1;
        num2=2;
        teststring='hello';//直接赋值,最后可以看到返回值就是赋的值
    }
    
    function test2() public view returns(uint8 num1,uint8 num2,string teststring){
        return (10,20,'hello2');//可以直接进行返回
    }
    
    function test3() public view returns(uint8 num1,uint8 num2,string teststring){
        num1=1;
        num2=2;
        teststring='hello';
        return (10,20,'hello2');//如果又赋值又返回,那么以最后为准
    }
    
    function test4() public view returns(uint8 num1,uint8 num2,string teststring1,string teststring2){
        teststring1='testnb1';
        teststring2='testnb2';
        //return (10+20,10*20,'hello2',teststring1+teststring2);//solidity不支持string直接连接
        return (10+20,10*20,teststring1,teststring2);
    }
}

运行结果
在这里插入图片描述

4. 变量作用域

结论:
1.如果不在函数内再次定义重名变量,那么函数内部对合约变量进行修改
2.for循环中可能会出现重定义情况,注意

contract areatest{
    uint public a=1;
    function areatest1(uint a) public view returns(uint){
        a=10;
        return a;
    }
    
    
    function areatest2(uint a) public view returns(uint){
        a=10;
       //for(uint a=0;a<10;a++){
            
       // }
        return a;
    }
    
    function areatest3() public  returns(uint){
        a++;
        return a;
    }
    
    function areatest4(uint a) public  returns(uint){
        a++;
        return a;
    }
    
    

}

运行结果
在这里插入图片描述

5.constant修饰符

结论
1.constant可在函数声明时使用,相当于view。不消耗燃料
但是此功能4.x版本可用,5.x版本废弃
2.constant只能用于全局变量
3.constant一旦声明函数的值就不可以修改
4.constant可以用于声明uint,int,bytes,string类型变量
代码

contract constanttest{
    uint public constant a=1;
    //function changetest() public{
    //    a=2; 函数内试图修改,结果编译报错
    //}
    //function changetest() public{
    //    uint constant test=2; //函数内无法声明constant变量
    // }
    int public constant b=2;
    bytes32 public constant c=0x2323;
    string public constant d='test';
    
}

6.构造函数

结论:
1.效果:在合约部署时自动调用一次,而且只能调用这一次
2.使用方法有两种
新式(推荐):constructor(参数列表) {}
旧式:function 合约名(参数列表) {}
如果传入参数,那么部署时也需要输入参数
3.用处:可以用来声明,赋值变量等等
代码

contract maketest{
    uint public a=1; //以下函数自行删除//测试,一个合约只能有零个或一个构造函数
    //function maketest(){
    //    a=100;
    //}
    
    function maketest(uint b) {
        b=200;
        a=b;
    }
    
    //constructor(){
    //    a=300;
    //}
    
    //constructor(uint b){
     //   b=400;
     //   a=b;
   //}

}

运行结果
部署时需要输入参数

7.modifier函数

结论:
1.整体构造

modifier 函数名 (参数列表){ 
    语句;
    _; //代表调用modifier的函数的语句
    语句;
}

2.如何调用modifier函数
function 函数名(参数列表) modifier函数名 后面的和普通函数一样
调用之后会将函数自动插入制定modifier函数中间的 _;位置运行,并且前后插入modifier函数已经写好的语句
多重modifier函数相互嵌套
3.应用场景:作判断,赋值等等
4.好处:实现代码重复使用
代码:

contract modifiertest{
    uint public a=1;
    modifier moditest1(){
        _;
        a=2;
    }
    
    modifier moditest2() {
        a=3;
        _;
    }
    
    function moditestfun1() moditest1{
        a=10;  //先运行a=10,再运行a=2,最后a=2
    }
    
    function moditestfun2() moditest2{
        a=20;//先运行a=3,再运行a=20,最后a=20
    }
    
    
    
    
    
    uint public testnum;
    
    function setvalue(uint _testnum){
        testnum=_testnum;  //设置testnum值
    }
    
    
    modifier judgetest1(uint judgenum){
        require(testnum>judgenum); //如果testnum值大于judgenum值则继续,否则跳出
        _;
    }
    
    function islarge1() judgetest1(3) public view returns(string){
        return "finished!";  //大于3时,输出提示
    }
    
    
    
    uint public x1=1;
    modifier taowa1(){
        x1=2;
        _;
        x1=3;
    }
    
    modifier taowa2(){
        x1=4;
        _;
        x1=5;
    }
    
    function taowatest1() taowa1 taowa2{
        //可以有多个modifier函数,顺序不同可能会造成影响
        //此处顺序为x1=2,x1=4,x1=5,x1=3,最后x1=3
    }
    
    function taowatest2() taowa2 taowa1{
         //此处顺序为x1=4,x1=2,x1=3,x1=5,最后x1=5
    }
}

运行结果太多就不放了

8.简单继承

结论
1.合约通过is来继承上一个合约可以继承的函数,参数等
2.合约可以连续继承,即
b is a,b继承了a的元素
c is b,c继承b的元素同时继承了a的元素
3.子合约继承父合约的变量以及函数时,如果子合约定义了同名变量或者函数,那么子合约的变量/函数会覆盖继承过来的
4.合约如果一次性要继承多个合约的话,通过逗号连接,如果有重复的变量名或者函数名以最后一个出现的为准。当然子合约出现的话最终还是以自合约为准
代码

contract jicheng1{
    uint a=1;
    string b='hello! i am jicheng1 !';
    function saygoodbye() public view returns(string){
        return 'goodbye';
    }
}

contract jicheng2 is jicheng1{
    function getall1() public view returns(uint,string ){
        return (a,b);
    }
    string c='hello! i am jicheng2 !';
    bytes2 d=0x1234;
}

contract jicheng3 is jicheng2{
    function getall2() public view returns(uint,string,string,bytes2){
        return (a,b,c,d);
    }
}

contract jicheng4 is jicheng3{
    
    uint a=1000;
    function getall2(uint a) public view returns(uint,string,string){
        return (a,b,c);
    }
    
}

运行结果

在这里插入图片描述
在这里插入图片描述

9.修饰符权限

结论:

是否继承 变量 函数
public,internal public,internal,external
private,external(变量实际没有external修饰符) private

注意:
1.不同说明:
internal只能在合约内部调用,合约外部不行
external只能在合约外部调用,合约内部不行
public合约内部,合约外部均可以调用
2.private不能够被继承,在合约外部不能被调用,但是在合约内部可以被调用
3.什么是合约内部/外部?
答:以remix举例
在内部就是指合约内部可以调用这个函数
在外部就是指合约部署之后可以在旁侧看到这个函数的按钮
4.一定要在合约内部调用external修饰函数有两种方法
a.使用 this.函数名 调用,这个相当于外部调用
b.再声明一个合约,在新的合约内部创建或者引用该合约即可

contract AuthoritySample{
    uint a=0;
    uint private b=1;
    uint public c=2;
    //uint external d=3;
    uint internal e=4;
    
    function privatetest() private view returns(string){
        return 'private';
    }
    
    function internaltest() internal view returns(string){
        return 'internal';
    }
    
    function externaltest() external view returns(string){
        return 'external';
    }
    
    function publictest() public view returns(string){
        return 'public';
    }
    
    function getexternal()public view returns(string){
        return this.externaltest(); //调用external方法1
    }
}

contract AuthorityTest is AuthoritySample{
    function showa() view returns(uint){
        return a;
    }
    
    //function showb() view returns(uint){
    //    return b;
    //}
    
    function showc() view returns(uint){
        return c;
    }
    
    // function showd() view returns(uint){
    //    return d;
    //}
    
     function showe() view returns(uint){
        return e;
    }

    
}

contract newexternal{
    AuthoritySample test=new AuthoritySample();
    function testexternal() public view returns(string){
        return test.externaltest();//调用external方法2
    }
}

运行结果
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

10.getter函数

结论:
1.如果在声明变量时使用public方法,那么合约会自动生成一个external类型的函数,返回值是public声明的值的类型,命名就是变量名。如果是mapping还会需要一个参数
2.如果我们在外面定义了这个函数,那么这个public变量自动生成的函数会自动消失。
代码

contract gettertest{
    uint public a=1;
    
    function a() public view returns(uint){
        return a;  //声明变量时相当于自动生成了这个函数
    }
    
    mapping(uint=>string) public xxx; //使用mapping时也生成,但需要输入参数
    function test2(){
        xxx[a]='hello';
    }    

}

运行结果
在这里插入图片描述

11.合约的销毁

结论:
1.函数通过selfdistrust(合约调用者地址,实际上就是msg.sender)
2.销毁了合约之后,合约内的函数就会失效,无法再被调用
代码

contract suicidecontract{
    uint public a=1;
    
    function suicidecontracttest() {
         selfdestruct(msg.sender);
    }
   
   function tets() public view returns(string){
       return 'function end here!';
   }
}

运行结果
销毁前
在这里插入图片描述
销毁后
在这里插入图片描述

本文所有代码

pragma solidity ^0.4.0;


contract funtest{
    
    
    /*function fun0() {
        
    }
    
    
    function fun0() {
        
    }*/
      uint public test= 0;
      
    function fun1(uint num1,uint num2) {
        test = 10;
    }
    
    
    function fun1(uint num1) {
        test = 20;
    }
    
    
    function fun2(uint a) {
        test = 100;
    }
    
    
    function fun2(string a) {
         test = 200;
    }
    
    
    
    function fun3(address a) {
        test=1000;
    }
    
    
    function fun3(uint160 a){
        test=2000;
    }
    
    
    
    
    function fun4(uint8 a){
         test=10000;
    }
    
    
    function fun4(uint16 a){
        test=20000;
    }
    
    
    
    
    function fun1test() public view returns(uint){
        fun1(1,2);
        return test;
    }
    
     function fun2test() public view returns(uint){
        fun2('asdasd');
        return test;
    }
    
    function fun3test() public view returns(uint){
        fun3(0x2e805eC48BdFBc458e7446058F94a315896A1cF6);
        return test;
    }
    
    //function fun3test2() public view returns(uint160){
        //uint160 temp=uint160(0x2e805eC48BdFBc458e7446058F94a315896A1cF6);
        //fun3(temp);
        //return temp;
    //}
    
    
    
    
    function fun4test() public view returns(uint){
        fun4(256);
        return test;
    }
   
    
    function reset() public{
        test = 0;
    }
    
}



contract nametest{
    
    uint public num;
    string public teststring;
    
    function setvalue(uint num1,string teststring1){
        num=num1;
        teststring = teststring1;
    }
    
    function test1(){
        setvalue(2,'b');
    }
    
    function test2(){
        setvalue({num1:3,teststring1:'c'});
    }
    
    function test3(){
        setvalue({teststring1:'d',num1:4});
    }
    
    //function wrongtest4(){
    //    setvalue({teststring1:'a'});
    //}
    
}



contract returntest{
    function test1() public view returns(uint8 num1,uint8 num2,string teststring){
        num1=1;
        num2=2;
        teststring='hello';
    }
    
    function test2() public view returns(uint8 num1,uint8 num2,string teststring){
        return (10,20,'hello2');
    }
    
    function test3() public view returns(uint8 num1,uint8 num2,string teststring){
        num1=1;
        num2=2;
        teststring='hello';
        return (10,20,'hello2');
    }
    
    function test4() public view returns(uint8 num1,uint8 num2,string teststring1,string teststring2){
        teststring1='testnb1';
        teststring2='testnb2';
        //return (10+20,10*20,'hello2',teststring1+teststring2);
        return (10+20,10*20,teststring1,teststring2);
    }
}


contract areatest{
    uint public a=1;
    function areatest1(uint a) public view returns(uint){
        a=10;
        return a;
    }
    
    
    function areatest2(uint a) public view returns(uint){
        a=10;
       //for(uint a=0;a<10;a++){
            
       // }
        return a;
    }
    
    function areatest3() public  returns(uint){
        a++;
        return a;
    }
    
    function areatest4(uint a) public  returns(uint){
        a++;
        return a;
    }
    
    
}


contract constanttest{
    uint public constant a=1;
    uint public a2=2;
    function constest() public constant returns(uint a){
        return a;
    }
    
    function constest2() public returns(uint a){
        return a2;
    }
    
    //function changetest() public{
    //    a=2;
    //}
    //function changetest() public{
    //    uint constant test=2;
    // }
    int public constant b=2;
    bytes32 public constant c=0x2323;
    string public constant d='test';
    
}

contract maketest{
    uint public a=1;
    //function maketest(){
    //    a=100;
    //}
    
    function maketest(uint b) {
        b=200;
        a=b;
    }
    
    //constructor(){
    //    a=300;
    //}
    
    //constructor(uint b){
     //   b=400;
     //   a=b;
   //}

}

contract modifiertest{
    uint public a=1;
    modifier moditest1(){
        _;
        a=2;
    }
    
    modifier moditest2() {
        a=3;
        _;
    }
    
    function moditestfun1() moditest1{
        a=10;
    }
    
    function moditestfun2() moditest2{
        a=20;
    }
    
    
    
    
    
    uint public testnum;
    
    function setvalue(uint _testnum){
        testnum=_testnum;
    }
    
    
    modifier judgetest1(uint judgenum){
        require(testnum>judgenum);
        _;
    }
    
    function islarge1() judgetest1(3) public view returns(string){
        return "finished!";
    }
    
    
    
    uint public x1=1;
    modifier taowa1(){
        x1=2;
        _;
        x1=3;
    }
    
    modifier taowa2(){
        x1=4;
        _;
        x1=5;
    }
    
    function taowatest1() taowa1 taowa2{
        
    }
    
    function taowatest2() taowa2 taowa1{
        
    }
}


contract jicheng1{
    uint a=1;
    string b='hello! i am jicheng1 !';
    function saygoodbye() public view returns(string){
        return 'goodbye';
    }
}

contract jicheng2 is jicheng1{
    function getall1() public view returns(uint,string ){
        return (a,b);
    }
    string c='hello! i am jicheng2 !';
    bytes2 d=0x1234;
}

contract jicheng3 is jicheng2{
    function getall2() public view returns(uint,string,string,bytes2){
        return (a,b,c,d);
    }
}

contract jicheng4 is jicheng3{
    
    uint x=1000;
    function getall2(uint z) public view returns(uint,string,string){
        return (x,b,c);
    }
    
}


contract AuthoritySample{
    uint a=0;
    uint private b=1;
    uint public c=2;
    //uint external d=3;
    uint internal e=4;
    
    function privatetest() private view returns(string){
        return 'private';
    }
    
    function internaltest() internal view returns(string){
        return 'internal';
    }
    
    function externaltest() external view returns(string){
        return 'external';
    }
    
    function publictest() public view returns(string){
        return 'public';
    }
    
    function getexternal()public view returns(string){
        return this.externaltest();
    }
}

contract AuthorityTest is AuthoritySample{
    function showa() view returns(uint){
        return a;
    }
    
    //function showb() view returns(uint){
    //    return b;
    //}
    
    function showc() view returns(uint){
        return c;
    }
    
    // function showd() view returns(uint){
    //    return d;
    //}
    
     function showe() view returns(uint){
        return e;
    }

    
}

contract newexternal{
    AuthoritySample test=new AuthoritySample();
    function testexternal() public view returns(string){
        return test.externaltest();
    }
}


contract gettertest{
    uint public a=1;
    
    function a() public view returns(uint){
        return a;
    }
    
    mapping(uint=>string) public xxx;
    function test2(){
        xxx[a]='hello';
    }
    
    
    
    
}


contract suicidecontract{
    uint public a=1;
    
    function suicidecontracttest() {
         selfdestruct(msg.sender);
    }
   
   function tets() public view returns(string){
       return 'function end here!';
   }
}

猜你喜欢

转载自blog.csdn.net/weixin_45067603/article/details/105896155