[Solidityのはじめ方] Part5: データ型(uint, address, string, bool など)

Solidityスマートコントラクト開発の第一歩

Solidityでスマートコントラクトを書く上で、データ型の理解は非常に重要です。データ型とは、変数にどんな種類の情報(数値、文字、アドレスなど)を格納するかを定義するものです。Solidityは静的型付け言語であり、変数を宣言する際には必ず型を指定する必要があります。これにより、コンパイラがコードの正しさをチェックしやすくなります。

Solidityのデータ型は、大きく値型 (Value Types)参照型 (Reference Types) に分けられます。

値型 (Value Types)

値型の変数は、データそのものを直接保持します。関数に渡したり、別の変数に代入したりすると、値がコピーされます。主な値型を見ていきましょう。

ブール型 (bool)

最もシンプルな型で、true (真) または false (偽) の2つの値のみを取ります。条件分岐などでよく使われます。デフォルト値は false です。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract BoolExample { bool public isAvailable = true; bool public defaultBool; // デフォルト値は false function toggleAvailable() public { isAvailable = !isAvailable; // true と false を切り替える }
}

整数型 (int / uint)

数値を扱うための型です。

  • int: 符号付き整数 (マイナスの値も扱える)
  • uint: 符号なし整数 (0以上の値のみ)

Solidityでは、格納できる値の範囲をビット数で指定できます (8ビットから256ビットまで、8ビット刻み)。例えば、uint8 は0から255 (28-1) まで、uint256 は0から 2256-1 までの非常に大きな数を扱えます。単に uintint と書いた場合は、uint256 および int256 と同じ意味になります。イーサリアムでは、トークンの量など負の値を取らない数値を扱うことが多いため、uint (特に uint256) がよく使われます。デフォルト値は 0 です。

注意: 整数型には扱える値の範囲に上限・下限があります。これを超えるとオーバーフローアンダーフローが発生し、予期せぬ動作や脆弱性の原因となることがあります (Step 5で詳しく学びます)。Solidity 0.8.0以降では、これらのチェックがデフォルトで有効になっています。
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract IntegerExample { uint256 public positiveNumber = 100; // 符号なし整数 (uint でも可) int public negativeNumber = -50; // 符号付き整数 uint8 public smallUint = 255; // 8ビット符号なし整数 uint public defaultUint; // デフォルト値は 0 function add(uint a, uint b) public pure returns (uint) { return a + b; }
}

アドレス型 (address / address payable)

Ethereumのアカウント (EOA: Externally Owned Account) やスマートコントラクトのアドレス (20バイトの値) を格納するための特別な型です。

  • address: 通常のアドレス型。残高の取得 (balance) などができます。
  • address payable: address 型の機能に加え、Etherの送信 (transfer, send) が可能なアドレス型です。Etherを受け取る関数を持つコントラクトや、Etherを送金する先の変数は payable である必要があります。

アドレス型のデフォルト値は 0x0000000000000000000000000000000000000000 (ゼロアドレス) です。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract AddressExample { address public owner; address payable public recipient; address public defaultAddress; // デフォルト値は 0x00...00 constructor(address payable _recipient) { owner = msg.sender; // スマートコントラクトをデプロイした人のアドレス recipient = _recipient; } function getOwnerBalance() public view returns (uint) { return owner.balance; // アドレスのETH残高を取得 } function sendEther(uint amount) public payable { // recipient に Ether を送信 (呼び出し元がEtherを付与する必要あり) bool success = recipient.transfer(amount); require(success, "Failed to send Ether"); }
}

固定サイズバイト配列 (bytes1 〜 bytes32)

固定長のバイトシーケンスを格納します。bytes1 は1バイト、bytes32 は32バイトのデータを保持できます。文字列よりもガス効率が良い場合があり、ハッシュ値の格納などによく使われます。デフォルト値は全てのバイトが 0x00 で埋められたものです。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract BytesExample { bytes1 public oneByte = 0xb5; // 1バイトデータ bytes32 public hashValue = 0x123...abc; // 32バイトデータ (例: Keccak256ハッシュ) bytes2 public defaultBytes2; // デフォルト値は 0x0000
}

列挙型 (enum)

ユーザーが定義できる型で、定数に名前をつけて管理しやすくします。例えば、コントラクトの状態などを分かりやすく表現できます。内部的には uint として扱われます (通常は uint8)。デフォルト値は最初に定義されたメンバー (以下の例では Pending) です。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract EnumExample { enum Status { Pending, Shipped, Delivered, Canceled } // 状態を定義 Status public currentStatus; // デフォルトは Status.Pending (0) function ship() public { require(currentStatus == Status.Pending, "Order must be pending to ship."); currentStatus = Status.Shipped; } function deliver() public { require(currentStatus == Status.Shipped, "Order must be shipped to deliver."); currentStatus = Status.Delivered; } function getStatus() public view returns (Status) { return currentStatus; }
}

参照型 (Reference Types)

参照型の変数は、データの値そのものではなく、データが格納されている場所 (メモリやストレージ) を指し示します。そのため、代入や関数の引数として渡す際に、データの場所に関する情報だけがコピーされ、データ自体がコピーされるわけではありません (ただし、ストレージとメモリ間での代入など、場所が変わる場合はコピーが発生します)。

参照型には、配列 (Arrays)、構造体 (Structs)、マッピング (Mappings)、文字列 (string)、動的バイト配列 (bytes) などがあります。これらは後のステップで詳しく学びますが、ここでは stringbytes について簡単に触れます。

文字列 (string)

UTF-8エンコードされた可変長の文字列を扱います。内部的には動的なバイト配列 (bytes) として扱われますが、文字列としての操作が可能です。ただし、Solidityの文字列操作は他の言語ほど機能豊富ではなく、ガス代も比較的高くなる傾向があります。デフォルト値は空文字列 "" です。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract StringExample { string public message = "Hello Solidity!"; string public defaultString; // デフォルト値は "" (空文字列) function updateMessage(string memory newMessage) public { message = newMessage; } // 文字列の連結 (ガス代が高め) function concatenate(string memory a, string memory b) public pure returns (string memory) { return string(abi.encodePacked(a, " ", b)); }
}

関数の引数やローカル変数として string を使う場合、memory または calldata というデータロケーションを指定する必要があります (Step 4で詳しく学びます)。

動的バイト配列 (bytes)

可変長のバイトシーケンスを格納します。任意のバイナリデータを扱うのに適しています。string と似ていますが、UTF-8エンコーディングを前提としません。デフォルト値は空のバイト配列 0x です。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
contract DynamicBytesExample { bytes public dynamicData; bytes public defaultBytes; // デフォルト値は 0x function setData(bytes memory newData) public { dynamicData = newData; } function getDataLength() public view returns (uint) { return dynamicData.length; }
}

今回はSolidityの基本的なデータ型、特に bool, uint/int, address, bytesN, enum, string, bytes について学びました。

ポイント

  • Solidityは静的型付け言語で、変数宣言時に型指定が必須。
  • 値型 (bool, int, uint, address, bytesN, enum) はデータを直接保持し、コピーされる。
  • 参照型 (string, bytes, 配列, 構造体, マッピング) はデータの場所を参照する。
  • 各型にはデフォルト値がある (例: boolfalse, uint0, address0x0...0, string"")。
  • 適切な型を選択することは、コードの可読性、安全性、そしてガス効率 (トランザクション手数料) に影響します。

これらのデータ型は、スマートコントラクトの状態を管理し、ロジックを組み立てるための基礎となります。次のステップでは、これらの型を使って変数や定数を定義する方法を学びます。

参考情報:

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です