0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Rustで "expected Option, found ()" エラーにハマった話

Posted at

目次

1. エラーになったコード

fn max_value(nums: &[i32]) -> Option<&i32> {
    if nums.is_empty() {
        None
    }

    let mut current_max = &nums[0];

    for num in nums.iter() {
        if num > current_max {
            current_max = num;
        }
    }

    Some(current_max);
}

fn main() {
    let nums = vec![10, 5, 42, 7];
    println!("{:?}", max_value(&nums));

    let empty = vec![];
    println!("{:?}", max_value(&empty));
}

このコードでは、max_value 関数を定義して、配列に含まれる最大値を返すことを意図している。配列が空である場合は None を返す。Rust では、戻り値の型を統一する必要がある。返す値があるか(=最大値が含まれる)ないか(=Noneである)場合は、Rust では Option 型を使い表記する。

返す値は正しく Option 型に含まれているものであるのに、このコードはエラーが発生してしまう。

2. エラーの原因と対策

上記のコードでは2つのエラーがある。

2.1. 早期リターンのNone

if nums.is_empty() {
    None
}

この書きかただとNoneという値を評価しただけで処理が続いてしまい、関数を抜けない。Rust の戻り値は return を使わない方法もあるが、これは関数の最後の式でないといけない。早期リターンの場合は、return None; のように return を使って書く必要がある。

2.2. Someにセミコロンをつけた

Rust では関数の最後の式が戻り値になるルールがある。

  • Some(current_max) (式) $\rightarrow$ そのまま戻り値
  • Some(current_max); (文)$\rightarrow$ 値が捨てられて () (=Unit 型)が返る

つまり、セミコロンを付けると「戻り値なし」と解釈されてしまい、型が合わなくなるので、Some(current_max) をセミコロンを外す必要がある。

あるいは、(1) と同様に return を使って書くこともできる。

3. 修正版コード

修正されたコードは次の通りになる。

fn max_value(nums: &[i32]) -> Option<&i32> {
    if nums.is_empty() {
        return None;
    }

    let mut current_max = &nums[0];

    for num in nums.iter() {
        if num > current_max {
            current_max = num;
        }
    }

    Some(current_max) // ← セミコロンなし
}

fn main() {
    let nums = vec![10, 5, 42, 7];
    println!("{:?}", max_value(&nums)); // Some(42)

    let empty: Vec<i32> = vec![];
    println!("{:?}", max_value(&empty)); // None
}

4. まとめ

  • Rust では最後の式が戻り値になる
  • 途中で関数を終わらせたいときは return を明示する
  • セミコロンをつけると「文」になり、Unit 型が返る
0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?