Option は、存在するかどうかわからないオプションの値を表す型です。Move の Option の概念は Rust から借用したもので、Move では非常に便利なプリミティブです。Option
は標準ライブラリで定義されており 、次のように定義されています。
File: move-stdlib/source/option.move
// File: move-stdlib/source/option.move
/// 存在するかもしれないし、しないかもしれない値の抽象化。
struct Option<Element> has copy, drop, store {
vec: vector<Element>
}
'std::option' モジュールはすべてのモジュールに暗黙的にインポートされるため、インポートを追加する必要はありません。
Option
は、型パラメータElement
を取るジェネリック型です。単一のフィールドvec
を持ち、これはElement
のベクターです。ベクターは長さ0または1を持つことができ、これを使用して値の存在または不在を表します。
Option
型には、Some
とNone
の2つのバリアントがあります。Some
バリアントは値を含み、None
バリアントは値の不在を表します。Option
型は、型安全な方法で値の不在を表現するために使用され、空または未定義の値を避けるために使用されます。
Option
型が必要な理由を示すために、例を見てみましょう。
ユーザー入力を受け取り、それを変数に格納するアプリケーションを考えてみます。いくつかのフィールドは必須で、いくつかはオプションです。
例えば、ユーザーのミドルネームはオプションです。ミドルネームの不在を表すために空の文字列を使用することもできますが、空の文字列とミドルネームの欠如を区別するために追加のチェックが必要になります。代わりに、Option
型を使用してミドルネームを表現することができます。
module book::user_registry {
use std::string::String;
/// ユーザーレコードを表す構造体。
public struct User has drop {
first_name: String,
middle_name: Option<String>,
last_name: String,
}
/// 指定されたフィールドで新しい `User` 構造体を作成。
public fun register(
first_name: String,
middle_name: Option<String>,
last_name: String,
): User {
User { first_name, middle_name, last_name }
}
}
上記の例では、middle_name
フィールドはOption<String>
型です。これは、middle_name
フィールドがString
値を含むか、空であるかのいずれかであることを意味します。これにより、ミドルネームがオプションであることが明確になり、空の文字列とミドルネームの欠如を区別するための追加のチェックが不要になります。
Option
型を使用するにはstd::option
モジュールをインポートしてOption
型を使用する必要があります。その後、some
またはnone
メソッドを使用してOption
値を作成できます。
// `option::some` は値を持つ `Option` 値を作成します。
let mut opt = option::some(b"Alice");
// `option.is_some()` は、オプションが値を含んでいる場合に true を返します。
assert!(opt.is_some(), 1);
// 内部の値は `borrow` および `borrow_mut` で借用できます。
assert!(opt.borrow() == &b"Alice", 0);
// `option.extract` はオプションから値を取り出し、オプションを空にします。
let inner = opt.extract();
// `option.is_none()` は、オプションが None の場合に true を返します。
assert!(opt.is_none(), 2);
The Move Book へ戻る