2017-06-27
오늘 공부한 내용
chapter 03 변수와 연산자
-------------------------------------
03-1)연산을 위한 연산자와 값의 저장을 위한 변수
<연산자와 변수를 이용한 데이터의 저장>
c언어에서는 '연산자(operator)'라는게 있는데 특정연산을 요구할 때 사용하는 약속된 기호를 가리켜 말한다.
덧셈연산을 하는 프로그램을 만든다고 가정할때 컴퓨터내에서 덧셈연산 명령을 한뒤에 그 연산값을 보여주려면 무엇을 이용하면될까?
바로 c언어에서 제공하는 변수를 이용하면 된다.
--> 덧셈연산을 하고 그 결과를 메로리 공간에 저장하고 메로리 공간에 저장된 값을 출력할때 --->변수 이용 !!
c언어에서 변수의 의미는
"값을 저장할 수 있는 메모리 공간에 붙은 이름, 혹은 메모리 공간 자체를 가리켜 변수라 한다."
예시를보자
--------------------------------------------------
int main(void)
{
int num; //num이라는 이름의 변수를 선언한것이다.
}
-----------------------------------------
이 문장의 int와 num의 의미하는바는 이렇다
int : 정수의 저장이 가능한 메모리 공간을 할당한다.
num : 그리고 그 메모리 공간의 이름을 num이라 한다.
아래를 보자
-----------------------------------------------------------
int main(void)
{
int num; //num이라는 이름의 변수를 선언한것이다. 전 포스팅에서 //는 주석이라고 설명했다.
num=20; //변수 num에 20저장
printf("%d",num); // 변수 num의 값 참조
}
-----------------------------------------------------------
C언어에서 =기호는 값의 대입을 뜻한다 num이라는 변수에 20이라는 값을 대입 한다는 것이지 num과 20이 같다는 뜻은 아니다.
그렇게 사용하려면 num==20;이라고 입력해야한다
=라는 기호를 가리켜 '대입 연산자' 라 하며,
대입 연산자의 오른편에 오는 값을 왼편에 오는 변수에 저장하는 형태로 사용이 된다.
<변수의 다양한 선언 및 초기화 방법>
c언어에서 '초기화'란 선언된 변수에 처음 값을 지정하는 것을 말한다.
그리고나서 초기화 이후에 저장된 값을 변경할 때에는 '대입'또는 '대입연산'을 진행한다고 한다.
int main(void)
{
int num; //num이라는변수의 선언
num=12; //변수 num을 12로 초기화
num=24; // 변수 num에 24를 대입
}
그런데 이렇게 변수선언해주고~초기화 해주지않고 C언어에서는 변수를 '선언과 동시에 초기화' 하는 것이 가능하다.
int num=12;
라고 코드를 작성해주면 변수 num이 메모리 공간에 할당되자마자 12로 초기화가된다.
둘 이상의 변수를 동시에 선언하는 것도 가능하고, 동시에 선언 미 초기화하는 것도 가능하다.
int num1,num2; //두 개의 변수를 선언
int num3=30, num4=40; // 두 개의 변수를 선언 및 초기화
그런데 왜 변수를 초기화할까??
--------------------------------------------------------
#include<stdio.h>
int main(void)
{
int num1,num2;
printf("num1: %d, num2:%d \n", num1,num2);
num1=10;
num2=20;
printf("num1:%d, num2: %d \n",num1,num2);
}
------------------------------------------------------------
을 실행시켜보면 초기화되지않은 지역변수를 사용했다고 에러가 뜨는데
"변수를 선언만하고 초기화하지 않으면 쓰레기 값이 저장된다."
여기서 말하는 쓰레기 값이란 '아무런 의미가 없는 값'을 뜻한다.
------------------------------------------------------
#include<stdio.h>
int main(void)
{
int num1,num2;
//printf("num1: %d, num2:%d \n", num1,num2); 이 코드를 주석처리하고 돌려보면
num1=10;
num2=20;
printf("num1:%d, num2: %d \n",num1,num2);
}
-----------------------------------------------------
num1=10 num2=20 이 출력된다.
그래서 변수를 선언과 동시에 0으로 초기화한 다음 이후 의미있는 값을 저장하기도 한다.
int num1=0;
int num2=0;
처럼 말이다 하지만 이것이 절대적으로 지켜야 할 규칙은 아니다.
<변수선언 시 주의사항>
"중괄호 내에 변수를 선언할 경우, 변수의 선언문은 중괄호의 앞부분에 위치해야 한다.:
중괄호의 시작부분에 변수의 선언문이 위치해야한다.
두 예시를 보자
int main(void)
{
int num1;
int num2;
num1=0;
num2=0;
}
변수 선언 이후에 초기화 문장이 등장한 예시인데 이 코드는 컴파일 에러를 발생시키지 않는다
그러나 아래와 같은 코드는 컴파일 에러를 발생시킨다.
int main(void)
{
int num1;
num1=0;
int num2;
num2=0;
}
num2의 선언문 앞에 변수의 선언이 아닌 문장이 등장했기 때문이다 따라서 중괄호의 앞부분에 변수의 선언문이 오도록 해야한다.
열혈c에 나오는 책에서는 1999년도에 발표된 c언어의 표준에서는 변수의 선언위치에 아무런 제한을 두지 않고 있기에 위의 코드도 컴파일이 되어야 하는 것이 정상이지만 최근에 발표된 컴파일러를 비롯해서, 상당수의 컴파일러가 변수의 선언문이 중괄호에 앞부분에 위치할 것을 요구하고 있으니 ..
순수하게 C언어로 프로그램을 작성하고자 한다면 컴파일러가 지원하는 변수의 위치에 상관없이 중괄호의 앞부분에 변수를 선언하는것이 좋다.
#변수이 이름을 지을 때 적용되는 규칙들
이거 진짜 변수 지을 때 기억해야한다. !!!!
특히
"변수의 이름을 정할 때에는 변수의 역할에 어울리는, 의미 있는 이름을 지어야 한다."
안그러면 나중에 내가 코드를 짜놓고도.. 이거 어디에 사용하려고 만든 변수인지 와닿지가 않는다 그래서 딱봐도 아 ! 하고 예상할수 있는 이름의
변수가 좋다.
1. 변수의 이름은 알파벳, 숫자, 언더바(_)로 구성된다.
2. C언어는 대소문자를 구분한다. 변수Age와 변수 age는 서로 다른 변수이다.
3. 변수의 이름은 숫자로 시작할 수 없고, 키워드도 변ㅅ의 이름으로 사용할 수 없다.
4. 이름 사이에 공백이 삽입될 수 없다.
<변수의 자료형(Data Type)>
변수는 두 가지 부류로 나뉜다.
1. 정수형 변수 : 정수의 저장을 목적으로 선언된 변수
char형, short형, int형, long형 변수로 나뉜다.
2. 실수형 변수 : 소수점 이하의 값을 지니는 실수의 저장을 목적으로 선언된 변수
float형, double형 변수로 나뉜다.
변수의 종류가 나뉘는 이뉴는 정수냐, 실수냐에 따라서 값이 메모리 공간에 저장 및 참조되는 방식이 다르기 때문이다
03-2) C언어의 다양한 연산자
<대입 연산자(=) 와 산술 연산자(+, -,*,/,%)>
두개의 피연산자를 요구하는 연산자를 가리켜 '이상 연산자(binary operator)'라 하는데 대입 연산자와 산술 연산자는 모두 이항 연산자들이다.
=연산자 : 연산자 오른 쪽에 있는 값을 연산자 왼쪽에 있는 변수에 대입한다 ex) num=20;
+연산자 : 두 피 연산자의 값을더한다. ex) num=4+3;
-연산자 : 왼쪽의 연산자 값에서 오른쪽의 피연산자 값을 뺀다. ex)num=4-3;
*연산자: 두 피연산자의 값을 곱한다. ex)num=4*3;
/연산자 : 왼쪽의 피 연산자 값을 오른쪽의 피 연산자 값으로 나눈다. ex) num=7/3;
%연산자 : 왼쪽의 피연산자 값을 오른쪽의 피연산자 값으로 나눴을 때 얻게 되는 나머지를 반환한다. ex)num=7%3;
그리고 함수 호출문의 인자절달 위치에 연산식이 올 수 있다.
무슨 말이냐면
----------------
int main (void)
{
int num1, num2;
printf("%d-%d=%d \n",num1,num2,num1-num2);
return 0;
--------------------------------
이렇게 인자전달 위치에 num1-num2와 같은 연산식이 올 수 있다.
<복합 대입 연산자>
이거 많이 쓴다 .
복합 대입 연산자는 다른 연산자와 합쳐진 형태의 대입 연산자를 말한다
+=, -= , /=, %=, <<=, >>=, &=, ^=, |=등이 있는데 산술 연산자와 합쳐진 복합 대입 연산자외에 나머지 연산자들은 다음에 !!!
a = a+b 를 a+=b라고 표현할수도 있는데 여기서 +=가 복합 대입 연산자이다.
a=a-b 는a-=b 와 같은 의미이다.
<부호연산의 의미를 갖는 +연산자와 -연산자>
+와 -가 덧셈, 뺄셈 의미 말고도 부호의 의미를 가진다.
그런데 부호 연산자와 복합 대입 연산자가 비슷해서 혼동하기 쉬우므로 잘 기억하자
num= -num2; //부호 연산자의 사용
num-= num2; //복합 대입 연산자의 의미이다. num=num-num2; 라는 뜻이다.
<증가, 감소연산자>
이거 헤깔리기 쉬운데 활용 빈도가 높아서 확실하게 이해해야한다.
이 연산자는 변수에 저장된 값을 1증가 및 감소시키는 경우에 사용되는 연산자이다. 단한연산자다.
++num : 값을 1 증가 후, 속한 문장의 나머지를 진행(선 증가, 후 연산)
num++ : 속한 문장을 먼저 진행한 후, 값을 1 증가(선 연산, 후 증가)
--num : 값을 1 감소 후 , 속한 문장의 나머지를 진행(선 감소, 후 연산)
num-- : 속한 문장을 먼저 진행한 후, 값을 1 감소(선 연산, 후 감소)
예제를 통해 보여주겠다.
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", num2);
return 0 ;
}
값이 어떻게 출력될까?
num1: 12
num1++: 12
num1: 13
num1: 12
++num1: 13
num1: 13
의 결과가 출력된다
예제 코드에 만약 괄호 연산이 있다면 후의 증가 및 후의 감소 연산 시에는
'소괄호의 영향을 받지 않고, 다음 문장으로 넘어가야만 비로소 값의 증가 및 감소가 이뤄진다'라는 사실을 기억하자.
<관계 연산자>
관계 연산자는 대소와 동등의 관계를 따지는 연산자이다.
관계 연산자는 '조건을 만족하면 1을, 만족하지 않으면 0을 반환'한다.
여기서 말하는 1과 0은 참(true)이면 1, 거짓(false)면 0을 대표하는 숫자이다.
1. < a<b a가 b보다 작은가?
2.> a>b a가b보다 큰가?
3.== a==b a와 b가 같은가?
4.!= a!=b a와 b가 다른가?
5.<= a<=b a가 b보다 같거나 작은가?
6.>= a>=b a가 b보다 같거나 큰가?
코드를 실행시켰을시에 0이 출력되었다는건 거짓을 의미하고 1을 출력한다면 참이라는것을 의미한다.
<논리 연산자>
1. && A&&B A와 B가 모두 참이면 연산결과로 참을 반환한다. (논리AND)
2. || A || B A와 B둘 중 하나라도 참이면 연산결과로 참을 반환 (논리 OR)
3. ! A! A가 참이면 거짓, A가 거짓이면 참을 반환(논리 NOT)
<콤마 연산자 , >
콤마 연산자는 둘 이상의 변수를 동시에 선언하거나, 둘 이사의 문장을 한 행(line)에 삽입하는 경우 사용되는 연산자다.
또한 둘 이상의 인자를 함수로 전달할 때도 인자의 구분을 목적으로 사용된다
즉 콤마 연산자는 다른 연산자와는 달리, 연산의 결과가 아닌 '구분'을 목적으로 주로 사용된다.
<연산자의 우선순위와 결합방향>
우리가 덧셈 뺄셈 곱셈 나눗셈 연산을 할때 우선순위가 존재하듯이
C언어에서도 연산자 우선순위 라는 것이 존재한다.
그런데 곱셈과 나눗셈이 동시에 있을때 곱셈과 나눗셈 중 무엇을 먼저 계산하는가?
곱셈과 나눗셈은 왼쪽에 먼저 등장하는 것부터 순서대로 계산한다.!! 이것을 바로 결합방향 이라고 한다.
즉 '우선순위가 동일한 두 연산자가 하나의 수식에 존재하는 경우, 어떠한 순서대로 연산하느냐를 결정해 놓은 것'이 바로 결합방향이다.
순위 |
연산기호 |
연산자 |
결합방향 |
1위 |
() |
함수호출 |
→
|
[] |
인덱스 |
-> |
간접지정 |
++(postfix) --(prefix) |
후위증가 및 감소 |
2위 |
++(postfix) --(prefix) |
전위증가 및 감소 |
← |
sizeof |
바이트 단위 크기 계산 |
~ |
비트 단위 NOT |
! |
논리 NOT |
-, + |
부호 연산(음수와 양수의 표현) |
& |
주소 연산 |
* |
간접지정 연산 |
3위 |
(casting) |
자료형 변환 |
← |
4위 |
*,/,% |
곱셈, 나눗셈 관련 연산 |
→ |
5위 |
+, - |
덧셈, 뺄셈 |
→
|
6위 |
<<, >> |
비트이동 |
→ |
7위 |
<, >, <=, >= |
대소비교 |
→ |
8위 |
==, != |
동등비교 |
→ |
9위 |
& |
비트AND |
→ |
10위 |
^ |
비트XOR |
→ |
11위 |
| |
비트OR |
→ |
12위 |
&& |
논리AND |
→ |
13위 |
|| |
논리OR |
→ |
14위 |
? : |
조건연산 |
← |
15위 |
=, +=, -=, *=, /=, %=, <<=, >>=, &=, ^=, |= |
대입연산 |
← |
16위 |
, |
콤마연산 |
→ |
03-3) 키보드로부터의 데이터 입력과 C언어의 키워드
<키보드로부터의 정수입력을 위한 scanf함수의 호출>
scanf 함수의 기본적인 사용법을 알아보자
int main(void)
{
int num;
scanf("%d", &num); //키보드로 입력된정수를 변수 num에 저장하라.
}
%d : 10진수 형태로 입력 받아서 --> &num : 변수 num에 저장하라!!
저번 시간에 나온 prinft함수에서 %d 는 서식문자이면서 '10진수 정수형태의 출력'을 의미한다고 했는데
그렇다면 scanf에서는 무슨의미일까??
prinft 에서의 %d와 반대로 '10진수 정수형태의 입력'을 뜻한다.
scanf함수도 입력의 형태를 다양하게 지정할 수 있다. 또 scanf함수는 공백을 기준으로 데이터를 구분한다.
scanf("%d %d %d", &num1, &num2, &num3); 라고 코드를 작성했다면 값을 입력할대 스페이스바, 탭 또는 엔터키를 입력해야한다.
<c언어의 표준 키워드(keyword)>
앞에서 소개한 int나 return와 같은 단어들은 이미 그 기능적 의미가 정해져 있는데,
기능적 의미가 정해져서 C언어의 문법을 구성하는 단어들을 가리켜 -->키워드(keyword)라고 한다.
키워드는 '프로그래머가 다른 용도로 사용할 수 없도록 제한되어 있다.' 그래서 변수나 함수의 이름으로 사용할 수 없다.