本文へスキップ
BecomeCoder

Solidityコース · 第2章 Solidityの基本 ― コントラクトを書いてみる · レッスン8

関数 ― 読む関数・書く関数

ブラウザで完結

導入

処理のまとまりが 関数(function) です。Solidity の関数には「台帳を書き換えるか / 読むだけか」で種類があり、これがガス(手数料)の有無に直結します。

説明

先ほどの count を増やしたり読んだりする関数を足してみます。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;

contract Counter {
    uint256 public count = 0;

    // 状態を書き換える関数(トランザクション:ガスがかかる)
    function increment() public {
        count = count + 1;
    }

    // 状態を読むだけの関数(view:外部からの呼び出しは無料)
    function getCount() public view returns (uint256) {
        return count;
    }

    // 引数だけで計算し状態に触れない関数(pure)
    function add(uint256 a, uint256 b) public pure returns (uint256) {
        return a + b;
    }
}
  • function increment() public { ... }count を書き換える。状態を変える処理はトランザクションとして記録され、ガスがかかる
  • view … 状態を読むだけで変更しないと約束する関数。外部から単に読むだけなら無料
  • pure … 状態を読みも書きもせず、引数だけで計算する関数。これも読み取りは無料。
  • returns (uint256) … 戻り値の型。複数返すこともできる。
graph TD
    F[関数] --> W["状態を変更する<br/>(書き込み)"]
    F --> R["状態を変更しない<br/>(読み取り)"]
    W --> TX["トランザクション<br/>ガスが必要・台帳更新"]
    R --> VP["view / pure<br/>外部呼び出しは無料"]

「お金(ガス)がかかるのは、台帳を書き換えるときだけ」――この原則を押さえると、view / pure を付ける意味が見えてきます。

やってみよう

getCount から view を外すと、コンパイラが「状態を変えていないなら view を付けなさい」と警告します。逆に view を付けた関数の中で count = ... と書き換えようとするとエラーになります。宣言した約束は言語が守らせてくれるわけです。

実際に動かしてみよう

下のエディタのコントラクトを「コンパイル & デプロイ」すると、ブラウザ内で本物のSolidityコンパイラ(solc)がコンパイルし、EVM(@ethereumjs)にデプロイされます。デプロイ後は public な関数がボタンになって並ぶので、引数を入れて呼び出すと戻り値・イベント・require のエラー(revert理由)まで確認できます。本文のコントラクトを書き換えて動きを試しながら進めましょう(コンパイラ本体は初回だけ読み込みに数秒かかります)。

Solidity — ブラウザ内でコンパイル & 実行

ブラウザ内で本物のSolidityコンパイラ(solc)とEVM(@ethereumjs)を動かす環境を読み込みます(コンパイラ本体は初回のコンパイル時に読み込むため、最初の実行だけ数秒かかります)。
スクロールして表示された時点でも自動で読み込まれます。