最新内容会更新在主站深入浅出区块链社区

原文链接:智能合约语言 Solidity 教程系列3 - 函数类型

Solidity 教程系列第三篇 - Solidity 函数类型介绍。

写在前面

Solidity 是以太坊智能合约编程语言,阅读本文前,你应该对以太坊、智能合约有所了解,如果你还不了解,建议你先看以太坊是什么

本文前半部分是参考Solidity 官方文档(当前最新版本:0.4.20)进行翻译,后半部分函数可见性( public, external, internal, privite )深度分析(仅针对专栏订阅用户)。

函数类型(Function Types)

函数也是一种类型,且属于值类型。

可以将一个函数赋值给一个函数类型的变量。还可以将一个函数作为参数进行传递。也可以在函数调用中返回一个函数。

函数类型有两类:内部(internal)和外部(external)函数

内部(internal)函数只能在当前合约内被调用(在当前的代码块内,包括内部库函数,和继承的函数中)。

外部(external)函数由地址和函数方法签名两部分组成,可作为外部函数调用的参数,或返回值。

函数类型定义如下:

function (<parameter types>) {internal|external} [pure|constant|view|payable] [returns (<return types>)]

如果函数不需要返回,则省去returns ()

函数类型默认是internal, 因此internal可以省去。但以此相反,合约中函数本身默认是public的, 仅仅是当作类型名使用时默认是internal的。

有两个方式访问函数,一种是直接用函数名f, 一种是this.f, 前者用于内部函数,后者用于外部函数。

如果一个函数变量没有初始化,直接调用它将会产生异常。如果delete了一个函数后调用,也会发生同样的异常。

如果外部函数类型在Solidity的上下文环境以外的地方使用,他们会被视为function类型。它会编码为20字节的函数所在地址,和在它之前的4字节的函数方法签名一起作为bytes24类型。

合约中的public的函数,可以使用internal和external两种方式来调用。

internal访问形式为f, external访问形式为this.f

成员: 属性 selector

public (或 external) 函数有一个特殊的成员selector, 它对应一个ABI 函数选择器。

```js

pragma solidity ^0.4.16;

contract Selector {
function f() public view returns (bytes4) {
return this.f.selector;
}
}
```

下面的代码显示内部(internal)函数类型的使用:

pragma solidity ^0.4.16;

library ArrayUtils {
// internal functions can be used in internal library functions because
// they will be part of the same code context
function map(uint[] memory self, function (uint) pure returns (uint) f)
internal
pure
returns (uint[] memory r)
{
r = new uint[](self.length);
for (uint i = 0; i < self.length; i++) {
r[i] = f(self[i]);
}
}
function reduce(
uint[] memory self,
function (uint, uint) pure returns (uint) f
)
internal
pure
returns (uint r)
{
r = self[0];
for (uint i = 1; i < self.length; i++) {
r = f(r, self[i]);
}
}
function range(uint length) internal pure returns (uint[] memory r) {
r = new uint[](length);
for (uint i = 0; i < r.length; i++) {
r[i] = i;
}
}
} contract Pyramid {
using ArrayUtils for *;
function pyramid(uint l) public pure returns (uint) {
return ArrayUtils.range(l).map(square).reduce(sum);
}
function square(uint x) internal pure returns (uint) {
return x * x;
}
function sum(uint x, uint y) internal pure returns (uint) {
return x + y;
}
}

下面的代码显示外部(external)函数类型的使用:

pragma solidity ^0.4.11;

contract Oracle {
struct Request {
bytes data;
function(bytes memory) external callback;
}
Request[] requests;
event NewRequest(uint);
function query(bytes data, function(bytes memory) external callback) public {
requests.push(Request(data, callback));
NewRequest(requests.length - 1);
}
function reply(uint requestID, bytes response) public {
// Here goes the check that the reply comes from a trusted source
requests[requestID].callback(response);
}
} contract OracleUser {
Oracle constant oracle = Oracle(0x1234567); // known contract
function buySomething() {
oracle.query("USD", this.oracleResponse);
}
function oracleResponse(bytes response) public {
require(msg.sender == address(oracle));
// Use the data
}
}

函数可见性分析

  • public - 任意访问
  • private - 仅当前合约内
  • internal - 仅当前合约及所继承的合约
  • external - 仅外部访问(在内部也只能用外部访问方式访问)

public 还是 external 最佳实践

请订阅区块链技术查看。

参考视频

我们也推出了目前市面上最全的视频教程:深入详解以太坊智能合约语言Solidity

目前我们也在招募体验师,可以点击链接了解。

参考文档

Solidity官方文档-类型

深入浅出区块链 - 系统学习区块链,打造最好的区块链技术博客

智能合约语言 Solidity 教程系列3 - 函数类型的更多相关文章

  1. 智能合约语言Solidity教程系列2 - 地址类型介绍

    智能合约语言Solidity教程系列第二篇 - Solidity地址类型介绍. 写在前面 Solidity是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所了解,如果你还不了解,建议你 ...

  2. 智能合约语言 Solidity 教程系列2 - 地址类型介绍

    Solidity教程系列第二篇 - Solidity地址类型介绍. 写在前面 Solidity是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所了解,如果你还不了解,建议你先看以太坊是 ...

  3. 智能合约语言 Solidity 教程系列10 - 完全理解函数修改器

    这是Solidity教程系列文章第10篇,带大家完全理解Solidity的函数修改器. Solidity系列完整的文章列表请查看分类-Solidity. 写在前面 Solidity 是以太坊智能合约编 ...

  4. 智能合约语言 Solidity 教程系列4 - 数据存储位置分析

    写在前面 Solidity 是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所了解, 如果你还不了解,建议你先看以太坊是什么 这部分的内容官方英文文档讲的不是很透,因此我在参考Soli ...

  5. 智能合约语言 Solidity 教程系列6 - 结构体与映射

    写在前面 Solidity 是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所了解, 如果你还不了解,建议你先看以太坊是什么 本系列文章一部分是参考Solidity官方文档(当前最新版 ...

  6. 智能合约语言 Solidity 教程系列5 - 数组介绍

    写在前面 Solidity 是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所了解, 如果你还不了解,建议你先看以太坊是什么 本文前半部分是参考Solidity官方文档(当前最新版本: ...

  7. 智能合约语言 Solidity 教程系列8 - Solidity API

    这是Solidity教程系列文章第8篇介绍Solidity API,它们主要表现为内置的特殊的变量及函数,存在于全局命名空间里. 写在前面 Solidity 是以太坊智能合约编程语言,阅读本文前,你应 ...

  8. 智能合约语言 Solidity 教程系列9 - 错误处理

    这是Solidity教程系列文章第9篇介绍Solidity 错误处理. Solidity系列完整的文章列表请查看分类-Solidity. 写在前面 Solidity 是以太坊智能合约编程语言,阅读本文 ...

  9. 智能合约语言 Solidity 教程系列7 - 以太单位及时间单位

    这是Solidity教程系列文章第7篇介绍以太单位及时间单位,系列带你全面深入理解Solidity语言. 写在前面 Solidity 是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所 ...

随机推荐

  1. git常用命令集合

    git命令 git init:创建一个仓库并在目录下新建一个.git的文件(初始化一个git仓库) 注:.git文件在工作区,是一个隐藏文件(用ls -ah命令查看),但是它不算工作区,而是git 的 ...

  2. Numpy数组索引为-1和None

    numpy的数组操作方便,可以用:来切片,用布尔数组或者布尔表达式来查找符合条件的数据,也可以用数组作为另一个数组的索引来查找指定的数据.但有时也会见到数组索引为-1和None.两者的用法如下: 1. ...

  3. linux下socket编程实例

    linux下socket编程实例一.基本socket函数Linux系统是通过提供套接字(socket)来进行网络编程的.网络的socket数据传输是一种特殊的I/O,socket也是一种文件描述符.s ...

  4. 实现基于LVS负载均衡集群的电商网站架构

    背景 上一期我们搭建了小米网站,随着业务的发展,网站的访问量越来越大,网站访问量已经从原来的1000QPS,变为3000QPS,网站已经不堪重负,响应缓慢,面对此场景,单纯靠单台LNMP的架构已经无法 ...

  5. 分页查询时,使用cookie保存上次的查询条件。jQuery实现方法以及中间遇到的坑

    今天做分页查询时需要在跳转页面时保存上次查询的条件,如下: 实现的大致思路就是用cookie本地保存. 其中需要用到jQuery.Cookie插件. 使用方法很简单: 存数据:$.cookie(“ke ...

  6. 【Kafka源码】处理请求

    [TOC] 在KafkaServer中的入口在: apis = new KafkaApis(socketServer.requestChannel, replicaManager, groupCoor ...

  7. 由浅入深学习springboot中使用redis

    很多时候,我们会在springboot中配置redis,但是就那么几个配置就配好了,没办法知道为什么,这里就详细的讲解一下 这里假设已经成功创建了一个springboot项目. redis连接工厂类 ...

  8. Visual Studio 生成DLL文件

    新建一个项目,在菜单栏中选择“项目”/“**属性”选项,该页面中将“输出类型”下拉列表中的选项选择为“类库”,然后重新生成一下该项目,或者在“Visual Studio 2008命令提示”中输入以下命 ...

  9. HTTP-FLV直播初探

    目前几种视频流的简单对比: 协议 httpflv rtmp hls dash 传输方式 http流 tcp流 http http 视频封装格式 flv flv tag Ts文件 Mp4 3gp web ...

  10. Linux下gcc编译生成动态链接库*.so文件并调用它

    动态库*.so在linux下用c和c++编程时经常会碰到,最近在网站找了几篇文章介绍动态库的编译和链接,总算搞懂了这个之前一直不太了解得东东,这里做个笔记,也为其它正为动态库链接库而苦恼的兄弟们提供一 ...