はじめに
この実験では、Rust における明示的な寿命注釈の概念を紹介します。これは、バローチェッカーによって参照の妥当性を判断するために使用されます。
注: 実験でファイル名が指定されていない場合、好きなファイル名を使用できます。たとえば、
main.rsを使用して、rustc main.rs &&./mainでコンパイルして実行できます。
明示的な注釈
バローチェッカーは、明示的な寿命注釈を使用して参照が有効である期間を判断します。寿命が省略されない場合、Rust は明示的な注釈が必要で、参照の寿命がどのようになるべきかを判断するために使用されます。寿命を明示的に注釈する構文は、次のようにアポストロフィ文字を使用します。
foo<'a>
// `foo` は寿命パラメータ `'a` を持っています
クロージャと同様に、寿命を使用するにはジェネリクスが必要です。また、この寿命構文は、foo の寿命が 'a の寿命を超えないことを示しています。型の明示的な注釈は、'a が既に導入されている場合、&'a T の形式を持ちます。
複数の寿命がある場合、構文は同様です。
foo<'a, 'b>
// `foo` は寿命パラメータ `'a` と `'b` を持っています
この場合、foo の寿命は 'a または 'b のいずれかを超えることはできません。
明示的な寿命注釈の使用例を次に示します。
// `print_refs` は、異なる寿命 `'a` と `'b` を持つ `i32` への 2 つの参照を取ります。
// これらの 2 つの寿命は、関数 `print_refs` と同じくらい長くなければなりません。
fn print_refs<'a, 'b>(x: &'a i32, y: &'b i32) {
println!("x is {} and y is {}", x, y);
}
// 引数を持たないが、寿命パラメータ `'a` を持つ関数。
fn failed_borrow<'a>() {
let _x = 12;
// エラー: `_x` は十分に長く生きていません
let y: &'a i32 = &_x;
// 関数内で寿命 `'a` を明示的な型注釈として使用しようとすると失敗します。
// なぜなら、`&_x` の寿命は `y` の寿命より短く、短い寿命を長い寿命に強制することはできないからです。
}
fn main() {
// 以下で借りるための変数を作成します。
let (four, nine) = (4, 9);
// 両方の変数の借り出し (`&`) を関数に渡します。
print_refs(&four, &nine);
// 借り出される入力は、借り手よりも長く生きなければなりません。
// 言い換えると、`four` と `nine` の寿命は、`print_refs` の寿命よりも長くなければなりません。
failed_borrow();
// `failed_borrow` には、`'a` が関数の寿命よりも長くなるように強制するための参照は含まれていませんが、`'a` は長いです。
// 寿命が制約されない場合、デフォルトは `'static` になります。
}
まとめ
おめでとうございます!明示的な注釈の実験を完了しました。技術力を向上させるために、LabEx でさらに実験を行って練習してください。