Help us understand the problem. What is going on with this article?

Solidityのダイヤモンド継承の解決

More than 1 year has passed since last update.

はじめに

Solidityは多重継承がサポートされています。当然、ダイヤモンド継承問題も発生します。今まではC#をはじめとした単一継承の言語しか扱ってこなかったので、備忘録がてら多重継承した際の動作をメモしておきます。なお、本記事はethereumやsolidity、継承の仕組みについては知っていることを前提にしているので、関連事項の説明は割愛します。

多重継承の解決

Sample1.sol
pragma solidity ^0.4.11;

contract Parent {
    event Log(string);

    function foo() public returns (string) {
        emit Log("Parent");
    }
}

contract Child1 is Parent {
    function foo() public returns (string) {
        emit Log("Child1");
        Parent.foo();
    }
}

contract Child2 is Parent {
    function foo() public returns (string) {
        emit Log("Child2");
        Parent.foo();
    }
}

contract GrandSon is Child1, Child2 {}

Solidityは、isキーワードを使用して継承を行います。上記のサンプルコードでは、Parentコントラクトを基底として、Child1Child2の2つの派生コントラクトを作成しています。さらに、その2つを多重継承したGrandSonコントラクトがあります。注目していただきたいには、Parentで定義されているfooメソッドはChild1Child2の両方でオーバーライドされている点です。

この状態でGrandSonfooメソッドを呼び出すと、実行されるのはChild2Parentfooメソッドだけです。つまり、child1fooメソッドは実行されません。これは、GrandSonが基本的にはChild1を知らないからです。GrandSonからChild1Child2両方のfoo`メソッドを呼び出すためには、以下のように書き換えます。

Sample2.sol
pragma solidity ^0.4.11;

contract Parent {
    event Log(string);

    function foo() public returns (string) {
        emit Log("Parent");
    }
}

contract Child1 is Parent {
    function foo() public returns (string) {
        emit Log("Child1");
        super.foo(); // superキーワード
    }
}

contract Child2 is Parent {
    function foo() public returns (string) {
        emit Log("Child2");
        super.foo(); // superキーワード
    }
}

contract GrandSon is Child1, Child2 {}

先ほどのコードと異なり、Child1Child2内でParentfooメソッドの呼び出しにsuperキーワードが使っています。superキーワードは、基底クラスを呼び出すためのキーワードです。それだけでなく、GrandSonコントラクトが継承している次の基底コントラクトも探索します。つまり、Child1fooメソッドも実行されます。GrandSonfooメソッドを呼び出すと、最終的にはChild1Child2Parentfooメソッドが呼び出されます。

まとめ

Solidityでダイヤモンド継承を行うと、最後に継承したコントラクトだけを辿って実行します。すべての継承ルートを辿りたい場合には、superキーワードを使って基底クラスのメソッドを呼び出す必要があります。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away