Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

よくあるエラーと対処法

Rust学習中に遭遇しやすいエラーとその解決方法をまとめました。

所有権関連のエラー

E0382: value borrowed after move

エラーメッセージ

error[E0382]: borrow of moved value: `s`
 --> src/main.rs:4:20
  |
2 |     let s = String::from("hello");
  |         - move occurs because `s` has type `String`
3 |     let s2 = s;
  |              - value moved here
4 |     println!("{}", s);
  |                    ^ value borrowed here after move

原因: 値が別の変数にムーブされた後に使用しようとしている

解決方法:

#![allow(unused)]
fn main() {
// 方法1: クローンする
let s = String::from("hello");
let s2 = s.clone();
println!("{}", s);  // OK

// 方法2: 参照を使う
let s = String::from("hello");
let s2 = &s;
println!("{}", s);  // OK
}

E0502: cannot borrow as mutable because it is also borrowed as immutable

エラーメッセージ

error[E0502]: cannot borrow `v` as mutable because it is also borrowed as immutable
 --> src/main.rs:4:5
  |
3 |     let first = &v[0];
  |                  - immutable borrow occurs here
4 |     v.push(4);
  |     ^^^^^^^^^ mutable borrow occurs here
5 |     println!("{}", first);
  |                    ----- immutable borrow later used here

原因: 不変参照がある間に可変操作をしようとしている

解決方法:

#![allow(unused)]
fn main() {
// 方法1: 不変参照を先に使い切る
let mut v = vec![1, 2, 3];
let first = &v[0];
println!("{}", first);  // ここで使い切る
v.push(4);              // その後で変更

// 方法2: インデックスを保存する
let mut v = vec![1, 2, 3];
let first_idx = 0;
v.push(4);
println!("{}", v[first_idx]);
}

E0499: cannot borrow as mutable more than once

エラーメッセージ

error[E0499]: cannot borrow `x` as mutable more than once at a time
 --> src/main.rs:4:17
  |
3 |     let r1 = &mut x;
  |              ------ first mutable borrow occurs here
4 |     let r2 = &mut x;
  |              ^^^^^^ second mutable borrow occurs here
5 |     println!("{}, {}", r1, r2);
  |                        -- first borrow later used here

原因: 可変参照を同時に複数作ろうとしている

解決方法:

#![allow(unused)]
fn main() {
// 方法1: 順番に使う
let mut x = 5;
let r1 = &mut x;
*r1 += 1;
// r1のスコープ終了

let r2 = &mut x;
*r2 += 1;

// 方法2: ブロックでスコープを分ける
let mut x = 5;
{
    let r1 = &mut x;
    *r1 += 1;
}
{
    let r2 = &mut x;
    *r2 += 1;
}
}

ライフタイム関連のエラー

E0106: missing lifetime specifier

エラーメッセージ

error[E0106]: missing lifetime specifier
 --> src/main.rs:1:33
  |
1 | fn longest(x: &str, y: &str) -> &str {
  |               ----     ----     ^ expected named lifetime parameter

原因: 複数の参照を受け取って参照を返す関数でライフタイムが不明

解決方法:

#![allow(unused)]
fn main() {
// ライフタイム注釈を追加
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
    if x.len() > y.len() {
        x
    } else {
        y
    }
}
}

E0597: borrowed value does not live long enough

エラーメッセージ

error[E0597]: `x` does not live long enough
 --> src/main.rs:4:9
  |
3 |     let r;
  |         - borrow later stored here
4 |         let x = 5;
5 |         r = &x;
  |             ^^ borrowed value does not live long enough
6 |     }
  |     - `x` dropped here while still borrowed

原因: 参照先がスコープを抜けて無効になる

解決方法:

#![allow(unused)]
fn main() {
// 参照先を外側のスコープに移動
let x = 5;
let r = &x;
println!("{}", r);
}

型関連のエラー

E0308: mismatched types

エラーメッセージ

error[E0308]: mismatched types
 --> src/main.rs:2:18
  |
2 |     let x: i32 = "hello";
  |            ---   ^^^^^^^ expected `i32`, found `&str`
  |            |
  |            expected due to this

原因: 期待される型と実際の型が一致しない

解決方法:

#![allow(unused)]
fn main() {
// 正しい型を使う
let x: i32 = 42;

// または型注釈を省略
let x = "hello";
}

E0277: the trait bound is not satisfied

エラーメッセージ

error[E0277]: the trait bound `MyStruct: std::fmt::Debug` is not satisfied
 --> src/main.rs:5:22
  |
5 |     println!("{:?}", my_struct);
  |                      ^^^^^^^^^ `MyStruct` cannot be formatted using `{:?}`

原因: 必要なトレイトが実装されていない

解決方法:

// deriveでトレイトを実装
#[derive(Debug)]
struct MyStruct {
    value: i32,
}

fn main() {
    let my_struct = MyStruct { value: 42 };
    println!("{:?}", my_struct);  // OK
}

Option/Result関連のエラー

cannot use ? in a function that returns ()

エラーメッセージ

error[E0277]: the `?` operator can only be used in a function that returns `Result` or `Option`
 --> src/main.rs:3:13
  |
3 |     let f = File::open("file.txt")?;
  |             ^^^^^^^^^^^^^^^^^^^^^^^ cannot use the `?` operator in a function that returns `()`

原因: ?演算子はResultOptionを返す関数でしか使えない

解決方法:

// 方法1: 関数の戻り値をResultにする
fn main() -> Result<(), std::io::Error> {
    let f = File::open("file.txt")?;
    Ok(())
}

// 方法2: matchでハンドリング
fn main() {
    match File::open("file.txt") {
        Ok(f) => { /* 処理 */ },
        Err(e) => eprintln!("Error: {}", e),
    }
}

// 方法3: unwrap(エラー時はパニック)
fn main() {
    let f = File::open("file.txt").unwrap();
}

method unwrap not found

エラーメッセージ

error[E0599]: no method named `unwrap` found for type `i32`

原因: unwrapOptionResultのメソッドで、普通の値には使えない

解決方法:

#![allow(unused)]
fn main() {
// Optionを返す関数の結果に使う
let v = vec![1, 2, 3];
let first = v.get(0).unwrap();  // get()はOption<&T>を返す
}

モジュール関連のエラー

E0432: unresolved import

エラーメッセージ

error[E0432]: unresolved import `crate::models`
 --> src/main.rs:1:5
  |
1 | use crate::models;
  |     ^^^^^^^^^^^^^ no `models` in the root

原因: モジュールが正しく宣言されていない

解決方法:

#![allow(unused)]
fn main() {
// main.rs または lib.rs でモジュールを宣言
mod models;  // これを追加

use crate::models::User;
}

ファイル構造:

src/
├── main.rs     # mod models; を宣言
└── models.rs   # または models/mod.rs

E0603: function is private

エラーメッセージ

error[E0603]: function `internal_function` is private
 --> src/main.rs:3:14
  |
3 | my_module::internal_function();
  |            ^^^^^^^^^^^^^^^^^ private function

原因: 非公開の関数にアクセスしようとしている

解決方法:

#![allow(unused)]
fn main() {
// 関数をpubにする
pub fn internal_function() {
    // ...
}
}

非同期関連のエラー

future cannot be sent between threads safely

エラーメッセージ

error: future cannot be sent between threads safely

原因: 非同期タスク内でSendでない値を使っている

解決方法:

#![allow(unused)]
fn main() {
// 方法1: Arcでラップ
use std::sync::Arc;
let data = Arc::new(data);

// 方法2: 値をクローンしてタスクに渡す
let data = data.clone();
tokio::spawn(async move {
    // data を使用
});
}

async block/function expected but found fn

エラーメッセージ

error: `await` is only allowed inside `async` functions and blocks

原因: asyncでない関数内でawaitを使っている

解決方法:

#![allow(unused)]
fn main() {
// 関数をasyncにする
async fn my_function() {
    let result = some_async_fn().await;
}
}

コンパイル時のヒント

未使用の変数警告

warning: unused variable: `x`
 --> src/main.rs:2:9
  |
2 |     let x = 5;
  |         ^ help: if this is intentional, prefix it with an underscore: `_x`

解決方法:

#![allow(unused)]
fn main() {
// 使う予定がない場合はアンダースコアを付ける
let _x = 5;

// または完全に無視
let _ = some_function();
}

デバッグのコツ

1. 型を確認する

#![allow(unused)]
fn main() {
// コンパイラに型を教えてもらう
let x: () = some_expression;  // エラーメッセージで型がわかる
}

2. 中間値を出力する

#![allow(unused)]
fn main() {
// dbg!マクロを使う
let result = dbg!(some_function());
// 出力: [src/main.rs:2] some_function() = 42
}

3. コンパイラの提案を読む

help: consider borrowing here: `&v`

Rustコンパイラは多くの場合、修正方法を提案してくれます。help:の行を注意深く読みましょう。


まとめ

エラー種別主な原因対処法
E0382ムーブ後の使用clone()または参照を使う
E0502借用ルール違反参照の使用順序を変える
E0106ライフタイム不明ライフタイム注釈を追加
E0308型の不一致正しい型を使う
E0277トレイト未実装deriveまたは手動実装

エラーメッセージを落ち着いて読み、コンパイラの提案に従うことが大切です。