コンテンツにスキップ

Rustの演算子

演算子とは、計算をしたり、値を比べたり、条件を組み合わせたりするときに使う記号のことです。C言語系の言語を使ったことがあれば、ほとんどは見覚えがあるはずです。

fn main() {
let a = 10;
let b = 3;
println!("{}", a + b); // 13
println!("{}", a - b); // 7
println!("{}", a * b); // 30
println!("{}", a / b); // 3(整数の割り算。余りは切り捨て)
println!("{}", a % b); // 1(余り)
}
▶ 実際に試してみよう

比較演算子は2つの値を比べて、結果を bool で返します。

fn main() {
let a = 5;
let b = 8;
println!("{}", a == b); // false
println!("{}", a != b); // true
println!("{}", a < b); // true
println!("{}", a > b); // false
println!("{}", a <= b); // true
println!("{}", a >= b); // false
}

これらは if の条件でいつも使います。詳しくは if…else のページで説明します。

論理演算子は、真偽値を組み合わせたり、反転させたりします。

fn main() {
let is_logged_in = true;
let is_admin = false;
println!("{}", is_logged_in && is_admin); // false — 両方が true でなければならない
println!("{}", is_logged_in || is_admin); // true — 少なくとも一方が true
println!("{}", !is_admin); // true — false を true に反転
}
▶ 実際に試してみよう
  • && — かつ(and):両側が true のときだけ true になります。
  • || — または(or):少なくとも一方が true なら true になります。
  • ! — 否定(not):true を false に、false を true にひっくり返します。

普通の = のほかに、変数の今の値をもとにして値を更新する省略形の演算子があります。

fn main() {
let mut score = 10;
score += 5; // score = score + 5 と同じ
score -= 2; // score = score - 2
score *= 3; // score = score * 3
score /= 2; // score = score / 2
println!("{score}");
}
▶ 実際に試してみよう

どの演算子も変数の値を変えるので、コンパイルを通すには変数に mut が必要なことを忘れないでください。

1つの式に演算子がいくつもあるとき、Rustは単純に左から右へ計算するわけではありません。学校の算数と同じように、*、/、% は + や - より先に計算されます。同じレベルの演算子は左から右へ計算されます。かっこはいつも最初に計算されるので、違う順番にしたいときはかっこを使いましょう。

fn main() {
let a = 2 + 3 * 4; // * が先:2 + 12
let b = (2 + 3) * 4; // かっこが先:5 * 4
let c = 10 - 4 - 3; // 同じレベルなので左から:(10 - 4) - 3
let d = 17 % 5 * 2; // 同じレベルなので左から:(17 % 5) * 2
let ok = 1 + 1 == 2 && 3 > 2; // 算術、次に比較、最後に &&
println!("{a} {b} {c} {d} {ok}");
}

実行結果:

14 20 3 4 true
▶ 実際に試してみよう

先に計算されるものから順に並べると、だいたい次のようになります。算術演算子(* / %、次に + -)、比較演算子(== != < > <= >=)、&&、||、そして最後に代入演算子(= += -= など)です。だから 1 + 1 == 2 && 3 > 2 は、かっこがなくてもちゃんと動きます。とはいえ、順番を考え込んでしまうようなら、かっこを付けましょう。かっこにコストはかからず、コードも読みやすくなります。

ある動画の長さは 125 秒です。それを変数に保存して、何分と何秒になるかを 2分5秒 のように表示してください。ヒント:整数の割り算 / で分が、% で残りの秒が求められます。

解答を見る
fn main() {
let total_seconds = 125;
let minutes = total_seconds / 60; // 2(余りは切り捨て)
let seconds = total_seconds % 60; // 5(余り)
println!("{minutes}分{seconds}秒");
}

実行結果:

2分5秒
▶ 実際に試してみよう

ゲームの score を 10 から始めます。省略形の代入演算子を使って、25 を足し、5 を引き、それから2倍にしてください。スコアと、それが 50 以上かどうか、そして 50 以上かつ偶数かどうかを表示します。ヒント:score % 2 == 0 なら偶数です。

解答を見る
fn main() {
let mut score = 10;
score += 25; // 35
score -= 5; // 30
score *= 2; // 60
println!("スコア: {score}");
println!("レベルクリア? {}", score >= 50);
println!("クリアかつ偶数? {}", score >= 50 && score % 2 == 0);
}

実行結果:

スコア: 60
レベルクリア? true
クリアかつ偶数? true
▶ 実際に試してみよう
  • 算術演算子:+ - * / %。整数の割り算は切り捨てになり、小数は出ません。
  • 比較演算子:== != < > <= >=。どれも bool を返します。
  • 論理演算子:&&(かつ)、||(または)、!(否定)。
  • 代入の省略形:+= -= *= /= は、mut の変数をその場で更新します。++ はありません。
  • * / % は + - より先に計算され、算術は比較や &&/|| より先に計算されます。迷ったらかっこを使いましょう。

理解度チェック

1. 両側が整数のとき、10 / 3 の結果はどうなりますか?

2. == や < のような比較演算子が必ず返す型はどれですか?

3. score += 5; をコンパイルするには何が必要ですか?

スコア: 0 / 3