기본 자료형


자료형                크기                        값의 표현 범위



정수형        char              1바이트                 -128이상 +127이하

정수형        short             2바이트                 -32,768 이상 +32,767 이하

정수형        int                 4바이트                 -2,147,483,648 이상 +2,147,484,647 이하

정수형        long              4바이트                 -2,147,483,648 이상 +2,147,484,647 이하

정수형        long long      8바이트                  매우 많음..경 이상

실수형        float              4바이트                +-3.4 * 10 ^-37 이상 +-3.4 * 10 ^+38 이하

실수형        double          8바이트                +-1.7 * 10 ^-307 이상 +-1.7 * 10 ^+308 이하 

실수형        long double  8바이트 이상        double이상의 표현범위


위처럼 많은 자료형이 있는 이유는 데이터의 표현방식이 다르므로 최소 둘 이상의 자료형이 필요하다.

또 메모리 공간의 적절한 사용을 위해 다양한 크기의 자료형이 필요하다. 5000개의 정수를 저장해야하는데 이 정수들이 short형으로 표현이 가능한 정수들이다.

이 정수들은 short형으로 저장한다면 5000 * 2 = 10000 byte가 소모된다. 반면 이를 int형으로 표현해서 저장한다면, 이의 두배에 해당하는 바이트 수가 소모되어 그만큼 메모리를 낭비하는 결과로 이어질 수 있다.


sizeof를 이용하면 자료형의 크기를 확인할 수 있다.


1
2
3
4
5
6
7
8
9
#include<stdio.h>
 
int main()
{
    int num1 = 15;
    printf("%d",sizeof(num1));
    
    return 0;
}

cs


출력결과 : 4 ( int형이기 때문에 4byte)


1
2
3
char num1 =1, num2 = 2;
    
printf("%d",sizeof(num1+num2));

cs


char형 덧셈결과로 반환된 값의 크기는 1바이트, short형 덧셈결과로 반환된 값의 크기는 2바이트가 될 거 같은데 출력결과는 4바이트이다.


이유는 일반적으로 cpu가 처리하기에 가장 적합한 크기의 정수 자료형을 int로 정의한다.


일반적으로 정수는 int형 , 실수는 double형 자료형을 쓴다.

CPU가 성능을 내기에 가장 좋은 연산이기 때문에! double형은 정밀도가 높아서 소수점 이하 15자리까지는 오차가 발생하지 않는다.


정수 자료형 이름에 한해서 unsigned선언을 추가하면 0 이상의 값만 표현하는 자료형이 되어 양의 정수 방향으로 두배 더 넓어지게 된다. 

예를들어 char형의 경우 unsigned char가 되면 표현할 수 있는 값의 범위는 0 ~ 255 이하가 되는 것이다.


unsigned는 정수 자료형에만 붙일 수 있다.

unsigned가 붙으면 MSB도 데이터의 크기를 표현하는데 사용이 된다.

따라서 표현할 수 있는 값이 0이상의 범위로 두배가 된다.


숫자를 이용해서 문자를 표현하는 다양한 방법이 있는데 C언어는 그 중 미국표준협회에서 지정 된 아스키코드라는 표준을 선택하였다.

아스키 코드는 알파벳과 일부 특수문자를 포함하여 총 128개의 문자로 이뤄져 있다.



ex)


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include<stdio.h>
 
int main()
{
    char ch1 = 'A'// 컴파일러에 의해 65로 변환
    char ch2 = 'C'// 컴파일러에 의해 67로 변환
    char ch3 = 65;
    char ch4 = 67;
    
    printf("%c %d\n",ch1,ch1);
    printf("%c %d\n",ch2,ch2);
    printf("%c %d\n",ch3,ch3);
    printf("%c %d\n",ch4,ch4);
    
    return 0;
}
 

cs


출력결과 : 

A 65

C 67

A 65

C 67


컴파일러도 아스키코드를 알고 있다. 프로그래머가 표현해 놓은 문자를 컴퓨터가 인식할 수 있도록 숫자를 바꿔버린다. 위의 예제를 통해 확인하자!

아스키 코드 값은 0이상 127이하로 이루어져 있기 때문에 char형 변수로 충분히 저장 가능하다. 문자를 저장할 때에는 int형 변수를 사용하지 않고 char형 변수를 사용한다.

int형으로도 가능하지만 메모리를 효율적으로 사용하기 위해서지 굳이 그렇게 할 필요는 없다.


상수

상수는 크게 이름이 있는 상수, 이름이 없는 상수 두가지로 나뉜다.


이름이 없는 리터럴 상수


1
2
3
4
5
6
7
8
9
#include<stdio.h>
 
int main()
{
    int num = 30 + 40;
    
    return 0;
}
 

cs


위의 코드에서 대입연산보다 덧셈연산이 우선이다. 덧셈이 진행되고 , 그 결과로 얻어진 값으로 변수 num을 초기화하게 된다. 그렇다는 것은 30+40의 연산을 CPU가 진행해야 한다는 뜻인데, 그러기 위해서는 30이라는 정수도 , 40이라는 정수도 메모리상에 존재해야 한다. 그래야 CPU의 연산대상이 될 수 있기 때문이다.
1. 정수 30과 40이 메모리 공간에 상수의 형태로 저장된다.
2. 두 상수를 기반으로 덧셈이 진행된다.
3. 덧셈의 결과로 얻어진 정수 70이 변수 num에 저장된다.

변수 num과 달리 할당된 메모리 공간에 이름이 없다는 것이다. 이렇든 이름이 없는 상수를 가리켜 리터럴 상수 또는 리터럴 이라고 한다.

1
2
3
4
5
6
7
8
9
10
11
#include<stdio.h>
 
int main()
{
    int num1 = 3 + 4;
    int num2 = 7 + num1;
    double num3 = 2.12 + 7.49;
    
    return 0;
}
 

cs


위의 에제에서 변수는 num1, num2, num3 3개이고, 상수는 3, 4, 7, 2.12, 7.49 총 5개이다.

이름이 있는 심볼릭 상수 : const상수

변수처럼 이름을 가지고 있는 상수, const키워드를 사용하여 만들 수 있고, 매크로를 이용하여 만들 수 있다. (매크로는 다음에!)

const를 이용하여 만드는 방법
1
2
3
4
5
6
7
8
9
#include<stdio.h>
 
int main()
{
    const int MAX = 100;
    const double PI =3.1415;
    
    return 0;
}

cs

MAX와 PI라는 이름의 상수를 선언하고 있다. 이처럼 이름을 지닌 상수를 심볼릭 상수라고 한다. 생성과 동시에 초기화를 하여야 한다.
선언과 동시에 초기화를 하지 않으면, 선언 시 쓰레기값이 들어가고 상수이기 때문에 값의 변경이 불가하여 변경하려고 하면 에러가 발생한다.!

자료형의 변환

char형 데이터의 표현방식을 int로 바꾸고나 ,int형 데이터의 표현방식을 double형으로 바꾸는 것이 바로 자료형의 변환이다. 
크게 두 종류로 나뉜다.
자동 형 변환(묵시적 형 변환)
강제 형 변환(명시적 형 변환)

대입연산자의 왼편과 오른편에 존재하는 두 피연산자의 자료형이 일치하지 않으면, 왼편에 있는 피연산자를 대상으로 형 변환이 자동으로 일어난다.

1
double num=245// int형 정수 245를 double형으로 자동 형 변환


cs


하지만 double형 상수가 int형으로 변환이 될 시에는 소수점 이하의 값은 다 버리고 정수만 남게 된다( 소수부의 손실 ) .!

1
int num=245.123// double형 실수 245.123을 int형 정수로 자동 형 변환

cs

출력결과 245


정수를 실수로 형 변환 하는 경우 - 오차가 존재할 수 있다.

실수를 정수로 형 변환하는 경우 - 소수점 이하의 값은 버려진다.

바이트 크기가 큰 정수를 바이트 크기가 작은 정수로 형 변환 하는 경우 ( int -> char ) - 변환하고자 하는 정수의 바이트 크기에 맞춰서 상위 바이트를 단순히 소멸시킨다. 이로인해 부호가 바뀔 수도 있으니 주의하라


double num1 = 5.15 + 19 ;


이 문장에서 사칙연산을 하려고 할 때, 이 둘의 자료형이 다르기 때문에, 자동 형변환이 일어난다.

이 때는 데이터의 손실을 최소화하는 방향으로 진행된다. int로 형 변환시 5 + 19 로 24가 되어 소수부의 손실이 발생된다. 하지만 double형으로 변환시

5.15 + 19.0 을 하면 오차가 존재하지만 정확한 연산이 된다.


명시적 형 변환:강제로 일으키는 형변환

1
2
3
4
5
6
7
8
9
10
11
12
#include<stdio.h>
 
int main()
{
    int n1=3, n2 = 4;
    double div = n1 / n2;
    printf("%f",div);
    
    
    return 0;
}
 

cs


위의 예제의 출력결과는 0.75 가 아닌 0.0000이 나온다.
연산결과의 자료형은 피연산자의 자료형과 일치하지 않기 때문이다. (정수형 나눗셈 결과의 몫 0)

내가 원하는 출력결과 0.75가 나오게 하려면 6행을

double div = (double)n1 / n2;

으로 바꾸어 주어야 한다. (double)n1은 변수 n1에 저장된 값을 double형으로 변환하라는 뜻이다. 
이렇게 되면 div = 3.0 / n2;로 바뀌고 이것은 형 변환 규칙에 의해 n2도 double형으로 자동 형 변횐이 된다.
div = 3.0 / 4.0 ; !
그 후 연산이 진행되고 double형 변수인 div에 결과가 저장된다.






'programming > C' 카테고리의 다른 글

C// 조건에 따른 흐름의 분기  (0) 2017.12.11
C // 반복문  (0) 2017.12.07
C // printf함수와 scanf 함수  (0) 2017.12.02
C // 변수와 연산자  (0) 2017.11.28
C // C의 기본  (0) 2017.11.27

+ Recent posts