算術演算子には以下のものがあります。
C言語の算術演算子、論理演算子、条件演算子、比較演算子、ビット演算子、べき乗の演算子、余りの演算子、などについて説明しています。優先順位一覧もあります。
算術演算子には以下のものがあります。
| 演算子 | 種別 | 例 | 意味 |
|---|---|---|---|
+ | 加算 | x + y | xにyを加える。 |
- | 減算 | x - y | xからyを引く。 |
* | 乗算 | x * y | xにyをかける。 |
/ | 除算 | x / y | xをyで割る。 |
% | 剰余算 | x % y | xをyで割った余りを求める。 |
整数の割り算では、小数点以下は切り捨てられます。被演算数が負の時の切り捨ての方向は機種に依存します。
+と-は同じ優先順位です。* / %も同じ優先度で、こちらのグループの方が+と-よりも優先順位が高くなります。
C言語で「余り」を求める演算子は%です。x % yはxをyで割った余りになります。この余りを求める演算子はfloatやdoubleに対しては使えません。被演算数が負の時の余りの符号は機種依存となります。
浮動小数点数に対して、余りを求めたい場合はfmod標準ライブラリ関数を使用します。文法は以下のとおりで、この関数はx/yの余りを返します。
#include <math.h>
double fmod(double x, double y);
C言語の論理演算子には以下のものがあります。
| 演算子 | 種別 | 例 | 意味 |
|---|---|---|---|
&& | 論理積(AND) | a && b | aとbが共に真の場合「真」 |
|| | 論理和(OR) | a || b | aまたはbが真の場合「真」 |
! | 否定(NOT) | !a | aが偽の場合「真」、aが真の場合「偽」 |
論理演算子を使う上で注意すべき点があります。それは、&&と||を使った場合、左側から式が評価され、その評価は全体の真、偽が決定した時点で終わる、ということです。これは、左側の式の真偽が、右側の式の実行条件になっている、ことを意味しますし、また、左側の式の真偽によって、右側の式が実行されないこともある、ということも意味します。
具体例を見てみましょう。
#include <stdio.h>
int main(int argc, char *argv[])
{
int i=0, j=0;
if (i && (j=j+1)) {
;
}
printf("%d,%d¥n",i,j);
return 0;
}
このプログラムをコンパイル、実行すると、下記のように表示されます。
0,0
iとjは0で初期化されています。if (i && (j=j+1)) {を評価するとき、iが0ですので、この時点で(i && (j=j+1))が偽と決定しj=j+1は実行されません。そのため、iとjが共に初期値の0のままで出力されます。
iの初期値を1と変えるとプログラムの実行結果は1,1となります。if (i && (j=j+1)) {を評価するとき、iが真ですので、この時点では(i && (j=j+1))の真偽が決定しません。そのためj=j+1が実行、評価され、jが1となります。
この仕様は、うっかり忘れてしまいがちですので注意しましょう。
条件演算子(じょうけんえんざんし、conditional operator)とは、条件によって異なる値を返す演算子のことです。被演算子が3つある3項演算子のひとつです。
| 演算子 | 種別 | 例 | 意味 |
|---|---|---|---|
? : | 条件演算子 | a ? b : c | aが真ならbが実行、aが偽ならcが実行。 |
例を見てみましょう。
cnt = (cnt < 100) ? cnt + 1 : 0;
この例ではcntが100未満なら1カウントアップされ、100以上ならcntが0となります。つまり、以下のif文と同じとなります。
if (cnt < 100) {
cnt = cnt + 1;
} else {
cnt = 0;
}
比較演算子は、関係演算子とも呼ばれ、C言語には下記のものがあります。
| 演算子 | 一般的な読み | 例 | 意味 |
|---|---|---|---|
< | 小なり | a < b | aはbより小さい |
<= | 小なりイコール | a <= b | aはb以下 |
> | 大なり | a > b | aはbより大きい |
>= | 大なりイコール | a >= b | aはb以上 |
== | イコール | a == b | aとbは等しい |
!= | ノットイコール | a != b | aとbは異なる |
比較の「==」と代入の「=」をうっかり間違えるケースがよくあります。気をつけましょう。また、ノットイコールは「<>」ではなく「!=」です。
ビット演算子はビット単位でデータを操作する演算子です。操作できる型は整数(char含む)のみです。
| 演算子 | 種別 | 例 | 意味 |
|---|---|---|---|
& | ビット毎のAND | a & b | aとbのビット単位のAND |
| | ビット毎のOR | a | b | aとbのビット単位のOR |
^ | ビット毎の排他的OR | a ^ b | aとbのビット単位の排他的OR |
<< | 左シフト | a << b | aをbビット分、左へシフト |
>> | 右シフト | a >> b | aをbビット分、右へシフト |
~ | ビット単位の反転 | ~a | aの各ビットを反転 |
ビット毎のAND演算子&は、指定のビットをマスクするためによく使われます。例えば、x = x & 0x0Fとするとxの下位4ビット以外は0になります。
ビット毎のOR演算子|は、指定のビットをオンにするためによく使われます。例えば、x = x | 0x02とするとxの下位2ビット目が1になります。
ビット毎の排他的OR演算子^は、2つの数の対応するビットが異なる時にそのビットが1になり、同じ時にそのビットが0になります。例えば、x = 0xE7 ^ 0x7Eならxは0x99になります。
シフト演算子<<と>>は左側の被演算数を右側の被演算数のビット数分シフトさせる演算子です。例えばx << 1ならxを左へ1ビットシフトします。空になるビット、今の場合は右から1ビット目、には0が入ります。unsignedの数の右シフトでは左から0が入ります。signedの数の右シフトでは、計算機によって、左から符号桁が入ってくる場合(算術シフト)と0が入ってくる場合(論理シフト)があります。
単項演算子~を使うとビットの反転が行えます。ビット単位で1が0に、0が1になります。~はチルダと読みます。~をニョロと呼ぶ人もいます。
C言語にはべき乗(累乗)の演算子はありません。べき乗を計算するときは標準ライブラリ関数のpow()を使用します。文法は以下のとおりです。xのy乗を返します。
#include <math.h>
double pow(double x, double y);
べき乗(累乗)の演算子は^でも**でもありません。うっかり間違えないように気をつけましょう。特に^の場合、コンパイルエラーとはなりませんので注意が必要です。
C言語の全演算子の優先度と結合規則の表を以下に示します。
| 演算子 | 結合規則 |
|---|---|
()(関数呼出しの演算子) [] -> . | 左から右 |
! ~ ++ -- +(単項) -(単項) *(単項) & (type)(キャスト演算子) sizeof | 右から左 |
* / % | 左から右 |
+ - | 左から右 |
<< >> | 左から右 |
< <= > >= | 左から右 |
== != | 左から右 |
& | 左から右 |
^ | 左から右 |
| | 左から右 |
&& | 左から右 |
|| | 左から右 |
?: | 右から左 |
= += -= *= /= %= &= ^= |= <<= >>= | 右から左 |
, | 左から右 |