Programming Language/C

3-2. 변수와 연산자 (연산자)

O773H 2018. 7. 13. 17:10
728x90

1-0. 연산자란 무엇인가?


'덧셈'하면 흔히 생각하는 것이 + 기호이다.

C언어를 이용해서 특정연산을 요구할 때 사용하는 약속된 기호를 가리켜 '연산자(operator)'라 한다.


1
2
3
4
5
6
7
8
#include <stdio.h>
 
int main(void)
{
    int num1 = 0;        // num1 변수를 선언 및 초기화
    num1 = 2 + 4;        // 2와 4의 합을 num1 변수에 저장
 
}
cs


6행에서 덧셈 연산을 수행하기 위한 연산자로 + 가 사용됐음을 알 수 있다.


1-1. 대입 연산자(=)와 산술연산자(+,-,*,/,%)


두 개의 피연산자를 요구하는 연산자를 가리켜 '이항 연산자(binary operator)'라 하는데, 대입 연산자와 산술 연산자는 모두 이항 연산자이다.


연산자                                            연산자의 기능                                       결합방향

   =              연산자 오른쪽에 있는 값을 연산자 왼쪽에 있는 변수에 대입한다.            <-

   

   +              두 연산자의 값을 더한다.                                                                ->


   -               왼쪽의 피연산자 값에서 오른쪽의 피연산자 값을 뺀다                           ->


   *               두 피연산자의 값을 곱한다.                                                             ->


   /               왼쪽의 피연산자 값을 오른쪽 피연산자 값으로 나눈다.                           ->


   %              왼쪽의 피연산자 값을 오른쪽의 피연산자 값으로 나눴을 때 얻게 되는       ->

                   나머지를 반환한다.   



'결합방향'이 의미하는 바는 잠시 후에 설명하겠습니다.


1-2. 복합 대입 연산자


다른 연산자와 합쳐진 형태의 대입 연산자도 존재하는데, 이를 가리켜 복합 대입 연산자라 한다. 종류는 다음과 같다.


+=,  -=,  *=,  /=,  <<=,  >>=,  &=,  ^=,  |=


이 중에서 산술 연산자와 합쳐진 복합 대입 연산자의 의미는 다음과 같다(나머지 연산자는 비트 연산자를 공부한 다음에 이해할 수 있다).


a = a + b    <-(동일 연산)->    a += b

a = a - b     <-(동일 연산)->    a -= b


.... 나머지도 똑같습니다 ...

1-3. 부호연산의 의미를 갖는 +연산자와 -연산자


+ 연산자와 -연산자는 이항 연산자로서 덧셈과 뺄셈을 의미하지만, 피연산자가 하나인 단항 연산자로서 부호를 뜻하기도 한다.


1
2
3
4
5
6
int main(void)
{
    int num1 = 5;    
    num1 = -num1;    // - 연산자를 이용해 num1 값의 부호를 바꾼다.

}
cs


1-4. 증감, 감소 연산자


이번에 소개하는 연산자는 변수에 저장된 값을 1 증가 및 감소시키는 경우에 사용되는 연산자이다. 단항연산자로서 활용의 빈도가 높다.


연산자                                            연산자의 기능                                       결합방향

++num              값을 1 증가 후, 속한 문장의 나머지를 진행(선 증가, 후 연산)            <-

   

num++              속한 문장을 먼저 진행한 후, 값을 1 증가(선 연산, 후 증가)               <-


--num               값을 1 감소 후, 속한 문장의 나머지를 진행(선 감소, 후 연산)             <-


num--               속한 문장을 먼저 진행한 후, 값을 1 감소(선 연산, 후 감소)                <-



++연산자와 --연산자는 이름 그대로 값을 1 증가 및 감소 시키는 연산자이다. 그런데 이 두 연산자는 삽입된 위치에 따라 그 위미가 달라지는데, 이는 아래 두 가지 예제로 살펴보겠다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <stdio.h>
 
int main(void)
{
    int num1 = 12;
    int num2 = 12;
    printf("num1 : %d \n", num1);
    printf("num1++: %d\n", num1++);            // 후위 증가
    printf("num1: %d\n\n", num1);
 
    printf("num2 : %d \n", num2);
    printf("++num2: %d\n"++num2);            // 전위 증가
    printf("num2: %d\n\n", num2);
}
cs


<실행 결과>

num1 = 12

num1++ = 12

num1 = 13


num2 = 12

++num2 = 13

num2 = 13




1
2
3
4
5
6
7
8
9
10
11
#include <stdio.h>
 
int main(void)
{
    int num1 = 10;
    int num2 = (num1--)+2;        // 후위 감소
 
    printf("num1 : %d \n", num1);
    printf("num2 : %d \n", num2);
    return 0;
}
cs


<실행 결과>

num1 : 9

num2 : 12



위 예제 6행을 살펴보자. num1 변수에 대해서 '선 연산, 후 감소'를 진행하고 있다.

그런데 여기서 소괄호가 채워져 있는데, 이는 수학의 소괄호와 의미가 같다(즉, 먼저 연산하라는 뜻이다).


int num2 = (num1--) + 2;


따라서 이는 다음과 같은 순서로 진행된다.


첫째. num1의 선 연산, 후 감소

둘째. 정수 2를 더해서 얻은 결과를

셋째. num2에 대입


* 그러면 여기서 num2에는 결과적으로 얼마가 저장될까?

아무리 '선 연산, 후 감소'라도 괄호까지 했으니 num1의 값이 감소한 상태에서 덧셈연산이 진행되는 게 아닐까? 아니다!! 

출력결과를 살펴보면 정수2와의 덧셈연산이 진행된 이후에 값이 감소했음을 볼 수 있다.

즉, 후위 증가 및 후위 감소 (선 연산, 후 증감) 연산 시에는 '소괄호의 영향을 받지 않고, 다음 문장으로 넘어가야만 비로소 값의 증가 및 감소가 이뤄진다'라는 사실을 알 수 있다.


1-5. 관계 연산자(<,>,==,!=,<=,>=)


관계 연산자는 대소와 동등의 관계를 따지는 연산자이다. '비교 연산자'라고도 한다. 두 개의 값을 비교하기 때문이다.


n1 == n2 ?         ( n1과 n2가 같은가?)


n1 != n2 ?          ( n1과 n2가 다른가?)


결합 방향은 모두 -> 이다.


(.. 나머지도 비슷합니다..)


관계 연산자들은 '조건을 만족하면 1을, 만족하지 않으면 0을 반환'한다. 여기서 1은 '참(true)', 0은 '거짓(false)'을 의미하는 대표적인 숫자이다.

"조건을 만족하면 '참(true)'을, 만족하지 않으면 '거짓(false)'을 반환한다." 는 표현을 기억하자!


1-6. 논리 연산자(&&, ||, !)


논리 연산자란 AND(논리곱), OR(논리합), NOT(논리부정)을 표현하는 연산자로서, 사용방법과 연산의 결과는 아래 설명하겠다.


 연산자

연산자의 기능

결합방향 

 &&

 예) A && B

 A와 B 모두 '참'이면 연산결과로 '참'을 반환 (논리 AND) 

->

 ||

 예) A || B

 A와 B 둘 중 하나라도 '참'이면 연산결과로 '참'을 반환 (논리 OR)

-> 

 !

 예) !A

 A가 '참'이면 '거짓', 'A가 '거짓'이면 '참'을 반환(논리 NOT)

<- 

(표를 만들 수 있었구나.....)



1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <stdio.h>
 
int main(void)
{
    int num1 = 10;
    int num2 = 12;
    int result1, result2, result3;
 
    result1 = (num1 == 10 && num2 == 12);
    result2 = (num1 < 12 || num2>12);
    result3 = (!num1);
 
    printf("result1: %d \n", result1);
    printf("result2: %d \n", result2);
    printf("result3: %d \n", result3);
    return 0;
}
cs


<실행 결과>

result1: 1

result2: 0

result3: 0


앞에서 살펴봤듯이 '참'일 경우는 1, '거짓'일 경우는 0을 반환한다고 했다.

우선 위 예제에서 9행을 살펴보자. 9행에서는 '관계연산'의 결과를 대상으로 '논리연산'을 진행하고 있다.

즉, 1차로 진행되는 것은 논리 연산자의 왼쪽과 오른쪽에 있는 관계연산이다. 따라서 다음의 사실을 알 수 있다.


"논리 연산자보다 관계 연산자가 먼저 진행이 된다!"


이렇듯 하나의 문장 안에 둘 이상의 연산자가 존재하는 경우 어떠한 연산을 먼저 진행하느냐에 대한 문제에 봉착하게 되는데, 이러한 부분의 혼란을 없애기 위해서 C언어는 '연산자 우선순위'라는 것을 정의하고 있다. 이 부분에 대해서는 뒤에 설명하겠다.


10행도 9행과 연산 순서가 동일하므로, 11행을 살펴보자.


result3 = (!num1);


여기서 num1에 1이 저장되어 있다면 result3에는 0이 저장되고, num1에 0이 저장되어 있다면 result3에는 1이 저장된다. 그렇다면 0도 1도 아닌 다른 값이 저장되어 있다면 result3에는 어떤 값이 저장될까? 이와 고나련해서 다음 사실을 알 필요가 있다.


"C언어는 0이 아닌 모든 값을 '참(true)'으로 간주한다."


즉, '거짓'을 의미하는 숫자는 0 하나로 유일하고, 0이 아닌 모든 숫자는 '참'으로 인식된다.


1-7. 콤마 연산자(,)


콤마 연산자는 둘 이상의 변수를 동시에 선언하거나, 둘 이상의 문장을 한 행(line)에 삽입하는 경우에 사용되는 연산자이다.

뿐만 아니라, 둘 이상의 인자를 함수로 전달할 때도 인자의 구분을 목적으로 사용된다.

이는 앞에서 많이 사용했으니 예제는 생략하겠다!


1-8. 연산자 우선순위와 결합방향


우리는 "수학에서 덧셈, 뺄셈 보다 곱셈, 나눗셈을 먼저 계산해야 한다는 사실"을 알고있다.


이것이 '연산자의 우선순위'이다.


또한, "곱셈과 나눗셈은 왼쪽에 먼저 등장하는 것부터 순서대로 계산한다"라는 것을 알고있다.

이것이 바로 '결합방향'이다.

즉, '우선순위가 동일한 두 연산자가 하나의 수식에 존재하는 경우, 어떤 순서대로 연산하느냐 결정해 놓은 것'이 바로 '결합방향'이다.


사칙연산의 결합방향은 '왼쪽에서 오른쪽'이라고 말할 수 있다. 이를 화살표로 그리면 -> 이 된다.

아래는 '우선순위'와 '결합방향'을 정리한 표이다.


순위 

연산기호 

연산자 

결합방향 

 1위

 () 

  함수호출 

 ->

 []

  인덱스 

->

  간접지정 

  직접지정

++ (postfix)

 --  (postfix) 

  후위증가 및 감소 

 2위

++ (prefix)

 --  (prefix) 

  전위증가 및 감소 

<- 

 sizeof

  바이트 단위 크기 계산 

  비트 단위 NOT 

 !

  논리 NOT 

 -, +

  부호 연산(음수와 양수의 표현) 

 &

  주소 연산 

 *

  간접지정 연산 

 3위

(casting) 

  자료형 변환 

<- 

 4위

*, /, % 

  곱셈, 나눗셈 관련 연산 

-> 

 5위

+, - 

  덧셈, 뺄셈 

-> 

 6위

<< . >> 

  비트이동

-> 

 7위

<.>,<=,>= 

  대소비교 

-> 

 8위

==,!= 

  동등비교 

-> 

 9위

  비트 AND 

-> 

 10위

  비트 XOR 

-> 

 11위

  비트 OR 

-> 

 12위

&& 

  논리 AND

-> 

 13위

|| 

  논리 OR 

-> 

 14위

? : 

  조건연산 

<- 

 15위

 =, +=, -=, *=, /=, %=, <<=, >>=, &=, ^=, |=

  대입연산 

<= 

 16위

 ,

  콤마연산 

-> 




728x90