C言語の演算子について
1.目的
目次
2.C言語の演算子の種類
・算術演算子
・代入演算子
・論理演算子
・比較演算子
・条件演算子
・ビット演算子
・複合演算子
これ以外にもある。
(1) 算術演算子
算術演算子 | |||
---|---|---|---|
演算子(記号) | 種別 | 例 | 意味 |
+ | 加算 | x + y | xにyを加える。 |
- | 減算 | x - y | xからyを引く。 |
* | 乗算 | x * y | xにyをかける。 |
/ | 除算 | x / y | xをyで割る。 |
% | 剰余算 | x % y | xをyで割った余りを求める。 |
使い方と実行結果:https://paiza.io/projects/w7OvE-mpqvljL_R42NiYoQ?language=c
(2) 代入演算子
代入演算子 | |||
---|---|---|---|
演算子(記号) | 種別 | 例 | 効果 |
= | 単純代入 | a=b | 代入 |
+= | 加算代入 | a+=b | 加算して代入 |
-= | 減算代入 | a-=b | 減算して代入 |
*= | 乗算代入 | a*=b | 乗算して代入 |
/= | 除算代入 | a/=b | 除算して代入 |
%= | 剰余代入 | a%=b | 乗余して代入 |
(3) 論理演算子
論理演算子 | |||
---|---|---|---|
演算子(記号) | 種別 | 例 | 意味 |
&& | 論理積(AND) | a && b | aとbが共に真の場合「真」 |
|| | 論理和(OR) | a || b | aまたはbが真の場合「真」 |
! | 否定(NOT) | !a | aが偽の場合「真」、aが真の場合「偽」 |
参考:論理演算子(ブール演算子)とは - 意味をわかりやすく - IT用語辞典 e-Words
(4) 比較演算子
比較演算子 | |||
---|---|---|---|
演算子 | 一般的な読み | 例 | 意味 |
< | 小なり | a < b | aはbより小さい |
<= | 小なりイコール | a <= b | aはb以下 |
> | 大なり | a > b | aはbより大きい |
>= | 大なりイコール | a >= b | aはb以上 |
== | イコール | a == b | aとbは等しい |
!= | ノットイコール | a != b | aとbは異なる |
使い方と実行結果:https://paiza.io/projects/AuQ9jku9QVG7lBRkQIq-Dw?language=c
(5) 条件演算子
条件演算子 | |||
---|---|---|---|
演算子(記号) | 種別 | 例 | 意味 |
? : | 条件演算子 | a ? b : c | aが真ならbが実行、aが偽ならcが実行。 |
使い方と実行結果:https://paiza.io/projects/DUERHNLofoyIB-Epbu-qug?language=c
(6) ビット演算子
ビット演算子 | |||
---|---|---|---|
演算子(記号) | 種別 | 例 | 意味 |
& | ビット毎の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,OR,XORの計算結果を示す)
A | B | A&B(AND) | A|B(OR) | A^B(XOR) |
---|---|---|---|---|
0 | 0 | 0 | 0 | 0 |
1 | 0 | 0 | 1 | 1 |
0 | 1 | 0 | 1 | 1 |
1 | 1 | 1 | 1 | 0 |
(7) 複合演算子
C言語では、下記のように略して書くことがある。
複合演算子 | |||
---|---|---|---|
演算子(記号) | 種別 | 例 | 意味 |
&= | ビット単位のAND代入 | a &= b | aとbのビット単位のANDして代入 |
|= | ビット単位のOR代入 | a |= b | aとbのビット単位のORして代入 |
^= | ビット単位の排他OR代入 | a ^=b | aとbのビット単位の排他的ORして代入 |
<<= | 左シフト代入 | a<<=b | 左にシフトして代入 |
>>= | 右シフト代入 | a>>=b | 右にシフトして代入 |
3.ビット演算子の使い方
これは、2進数で考えて使用する。(0bというのは2進数を示す)
例:0b0011 & 0b0101 = 0b0001
0b0011 | 0b0101 = 0b0111
0b0011^ 0b0101 = 0b0110
となる。
・ A << B は、A の値を B ビットだけ左にシフト
(Bの分だけ、0を付ける。)
例:0b1<<3 は、0b1000
0b10011011 << 3 は 0b11011000
・ A >> B は、A の値を B ビットだけ右にシフト
例:0b10011010 >> 2 は 0b00100110
・ ~Aは、Aのビットパターンを反転する。
例:~0001は1110
~001000は、110111
※ビットパターンの反転は、整数の補数を求める。
補数:加算するとすべてのビットが1(ON)になる値。
例2:0001 & ~0001 = 1111 と、すべてが1になる。
※ビット列を反転すると、
・符号なしでは整数で加算すると最大値
・符号付き整数では、加算すると-1になる。
このビット演算子は、組み込みでは、
レジスタ操作や通信を行う際に非常によく使う。
4.複合演算子の使い方
例1:変数Aのnビット目を1にしたい場合どう書くか。
A = 0b0010
n = 3 とし、 3ビット目を1にするつまり、A= 0b1010になるためには、
A と0b1000のORを取ってやればよい。
※0b0010 | 0b1000 = 1010
よって、1<<3で0b01000を作成
それをAとORを取る。
式で書くと。
A = A|1<< 3
これを複合演算子で書くと。
A |= 1<<3 となる。
よって、変数Aのnビット目を1にしたい場合
A |= 1<< n とすればよい。
確認:https://paiza.io/projects/fqABB39C1He0rRgQ4WaIVg?language=c
例2:変数Aのnビット目を0にする。
A = 0b1110
n = 3 とした場合
3ビット目を0(A= 0b0110)になるためには、
Aと0111のANDを取ればよい。
※0b1110 & 0b0111 = 0b0110
よって、~(1<<3)で0b0111を作成
それをAとANDを取る。
式で書くと。
A = A& ~ (1<<3)
これを複合演算子で書くと。
A&=~(1<<3)となる。
よって、変数Aのnビット目を0にする場合
A&=~(1<<n) とすればよい。
確認:https://paiza.io/projects/EUCDMN-xEaxWbxhM8C0BhQ?language=c
これらの考え方は、組み込みのレジスタ操作などに使える。
5.プログラム作成(論理演算子と比較演算子の確認)
#include <stdio.h> int main(void){ // Your code here! int b=6; int c=7; //論理演算子 printf("b=%d,c=%d\n",b,c); if(b>6 && c>6) //b>6かつc>6か確認 { printf("b>6かつc>6である。\n");//b>6とc>6を満たす時実行 }else { printf("b>6かつc>6ではない。\n");//b>6とc>6を満たさない時実行 } if(b>6 || c>6) //b>6又はc>6か確認 { printf("b>6またはc>6である。\n");//b>6かc>6のどちらかを満たす時実行 }else { printf("b>6またはc>6ではない。\n");//b>6、c>6のどちらかも満たさない時実行 } // !がついてるので、ノットイコールの時 if(!(b==6)) //b = 6ではないか確認 { printf("b=6ではない。\n"); //b = 6でない時実行 }else { printf("b=6である。\n"); //b = 6の時実行 } }
実行結果:https://paiza.io/projects/AuQ9jku9QVG7lBRkQIq-Dw?language=c
6.プログラム作成(条件演算子の確認)
#include <stdio.h> int main(void){ // Your code here! int a=7; int b=7; int c=6; int d = 0; printf("a=%d,b=%d,c=%d\n",a,b,c); //条件演算子 //a==b?A:Bは、a==bの時Aを実行、a==bではない時Bを実行 a == b ? printf("a=bである\n") : printf("a=bじゃない\n"); b == c ? printf("b=cである\n") : printf("b=cじゃない\n"); //d=(a==b)?1:0は、a==bの時、d=1、a==bでは無い時、d=0 d=(a==b) ? 1 : 0; printf("d=%d\n",d); //変数代入 a = 7; b = 8; //aがbより大きい時 a = a //aがbより大きくない時 a = b とする。(最大値上限設定などに使える) a = a>b?a:b; printf("a = %d\n",a); }
実行結果:https://paiza.io/projects/DUERHNLofoyIB-Epbu-qug?language=c
7.プログラム作成(ビット演算子の確認)
#include <stdio.h> //2進数変換関数 //引数:数値 //機能:入力した数値の2進数をprintfで出力する。 void second(int decimal) { /* 変数の宣言 */ int binary = 0; int base = 1; /* 10進数を2進数に変換 */ while(decimal>0){ binary = binary + ( decimal % 2 ) * base; decimal = decimal / 2; base = base * 10; } /* 変換した2進数の出力 */ printf("%d\n", binary); } int main(void){ int a = 0b1000|0b0100 ; printf("0b1000 | 0b0100="); second(a); int b = 0b1000&0b1100; printf("0b1000 & 0b1100="); second(b); int c = a<<1; printf("1100<<1 ="); second(c); int d = a>>1; printf("1100>>1 ="); second(d); }
実行結果:https://paiza.io/projects/6EWx-frf60ZGloPEJMxjAA?language=c
8.プログラム作成(ビット演算子と複合演算子の確認)
上記4.複合演算子の使い方の内容を出力で確認するプログラム
#include <stdio.h> //2進数変換関数 //引数:数値 //機能:入力した数値の2進数をprintfで出力する。 void second(int decimal) { /* 変数の宣言 */ int binary = 0; int base = 1; /* 10進数を2進数に変換 */ while(decimal>0){ binary = binary + ( decimal % 2 ) * base; decimal = decimal / 2; base = base * 10; } /* 変換した2進数の出力 */ printf(" 2進数 = %d\n", binary); } int main(void){ //変数A,Bのnビット目を1にするプログラム int A; int B; int n; A = 0b0010; B = 0b0010; n = 3; A = A|1<<3; printf("A = %d\n",A); second(A); B|=1<<n; printf("B = %d\n",B); second(B); }
実行結果:https://paiza.io/projects/fqABB39C1He0rRgQ4WaIVg?language=c
#include <stdio.h> //2進数変換関数 //引数:数値 //機能:入力した数値の2進数をprintfで出力する。 void second(int decimal) { /* 変数の宣言 */ int binary = 0; int base = 1; /* 10進数を2進数に変換 */ while(decimal>0){ binary = binary + ( decimal % 2 ) * base; decimal = decimal / 2; base = base * 10; } /* 変換した2進数の出力 */ printf(" 2進数 = %d\n", binary); } int main(void){ //変数A,Bのnビット目を1にするプログラム int A; int B; int n; A = 0b1110; B = 0b1110; n = 3; A = A & ~(1<<3); printf("A = %d\n",A); second(A); B&=~(1<<n); printf("B = %d\n",B); second(B); }
実行結果:https://paiza.io/projects/EUCDMN-xEaxWbxhM8C0BhQ?language=c
参考記事:
関連記事
C言語:
・組み込みの為のC言語基礎知識1(printf) - Project_OKI’s diary
・C言語基礎知識2(for分で処理を繰り返す) - Project_OKI’s diary
・C言語基礎知識3(配列) - Project_OKI’s diary
・知らないと損するお金の話(ふるさと納税、確定申告とワンストップ納税どっちが得?) - Project_OKI’s diary
・C言語基礎知識6(関数) - Project_OKI’s diary
・C言語基礎知識7(構造体1) - Project_OKI’s diary
・C言語基礎知識8(enum:列挙型) - Project_OKI’s diary
・C言語基礎知識9(typedef) - Project_OKI’s diary