2023-01-01 15:20:17 +09:00
Some(T)がタプル構造体だから(だと思う)。 Rust弱者が無理して考えたら余計分からなくなった。読む価値はないです
let some_string: Option<&str> = Some("こんな感じのコードを");
if let Some(string) = some_string {
println!("{}よく見かける", string);
}
ちょっと突っ込んだコードをRustで書こうとするとResultとOptionからは逃れられないわけで、雰囲気で使ってるのを改めたかった。
RustでNullを表現できる感じの列挙体で、値はSome(T)
かNone
を取る…みたいな理解をしてる。
ファイルをロードしたりとかで値が無になりうる処理の返り値はこれに包む。
let x = 0
という文では、letの右辺でパターンマッチングがされてる(らしい)。
The Bookによると、let a = b
はつまるところlet パターン = 式
をやってるっぽい。
左辺のパターンに右辺の式がマッチしたら束縛するとかなんとか。
で、上のコードif let Some~
云々はこれをifにしただけであって"もしもletによるマッチが成功したら"後ろのブロックを実行するみたいな感じ?
ここまで書いてて思ったことがあるので試す。
if let 1 = 1 {
println!("これは通る?");
}
ちゃんとif let
は成功して中身のprintln!が実行される。これをifを除いてlet 1 = 1;
にすると通らないんだけど、1は変数じゃなく束縛できない相手(リテラル)だから落ちてるみたいな認識でいいんだろうか。The Book途中で読むのやめちゃったせいで理解甘い所あるなと思った、今度読み直す
パターン記法では構造体とかも左辺に使えるからこんなコードも通る。
struct Pos {
x: i32,
y: i32,
}
let Pos { x, y } = Pos { x: -16, y: 0 };
println!("x: {}, y: {}", x, y);
これを省略していったのがlet x = Pos { x: -16, y: 0 }
とかそういう一般的な変数の宣言っぽそう。
上の記法をOptionに当てはめるとlet Some(x) = Some(128)
みたいな事になるわけで、右辺のSome(128)
は左辺のSome(x)
にマッチするので変数xに128が代入される。
ただ、Optionの場合はNoneの可能性がある(論駁可能性)のでletを平たく置いただけではコンパイルエラーになる。
だからif let
とかlet~else
としてパターンにマッチした場合のみ実行する必要があったんですね。
Rustの仕様気持ち良すぎだろ!