[C언어] 11. 변수 유효범위, 메모리 영역과 변수
이번에는 C언어의 변수 유효범위에 대해 알아보자.
전역변수와 지역변수
변수의 유효범위(scope)
1)변수의 유효범위(scope)란 👉 변수가 사용될 수 있는 범위
- 지역 유효 범위(local scope) : 함수, 블록
- 전역 유효 범위(global scope) : 프로젝트, 파일
변수의 선언 위치에 따라 변수 범위가 결정
범위에 따른 변수의 구분
1) 전역변수(global variable)
- 함수 외부에서 선언되는 변수 => 외부변수
- 전체 전역변수 : 프로젝트의 모든 파일에서 사용 가능한 변수
- 파일 전역변수 : 선언된 파일에서만 사용 가능한 변수
- 자동으로 초기값이 자료형에 맞는 0으로 지정
- 함수나 블록에서 전역변수와 같은 이름으로 지역변수 선언 가능
- 프로젝트의 다른 파일에서 참조 가능
extern
2) 지역변수(local variable)
- 함수 또는 블록에서 선언된 변수
- 함수 : 선언된 함수 내부에서 사용 가능한 변수
- 블록 : 선언된 블록 내부에서 사용 가능한 변수
- 지역변수가 할당되는 메모리 영역 :
stack(스택)
- 내부변수, 자동변수(automatic variables)
- 선언된 부분에서 자동으로 생성되고 함수나 블록이 종료되는 순간 메모리에서 자동 제거
- 선언 후 초기화하지 않으면 쓰레기 값이 저장
- ex) 함수의 매개변수, 블록 내부에서 선언한 변수
int main()
{
//지역변수 선언
int n = 10;
//for문 내부의 블록지역변수, 이름만 같은 다른 변수
for(int n = 0; n < 5; n++)
printf("%d ", n); //1 2 3 4 5
printf("\n");
printf("%d ", n); //10
}
정적변수와 레지스터변수
기억부류에 따른 변수의 구분
1) 기억부류(storage class)
- 변수는 기억 부류에 따라
- 할당되는 메모리 영역 결정
- 메모리의 할당 및 제거시기 결정
- 4가지 기억 부류 :
auto
,register
,static
,extern
기억부류 종류 | 전역변수 | 지역변수 | 사용방식 | 변수선언 시 초기화 | 기타 |
---|---|---|---|---|---|
auto | X | O | auto int a | 초기값 저장 가능 | 생략가능 |
register | X | O | register int a | 초기값 저장 가능 | |
static | O | O | static int a | 초기값 저장 가능 | |
extern | O | X | extern int a | 초기값 저장 불가능 |
모든지역변수 = auto가 생략된 자동변수
2) 기억부류에 따른 변수의 구분 키워드에 따라 결정
register
: 레지스터 변수static
: 정적변수auto(생략가능)
: 모든 지역변수extern
변수
레지스터 변수
1) 레지스터 변수란
- 키워드
register
를 자료형 앞에 넣어 선언, 지역변수에만 이용 가능 - 변수의 저장공간이 일반 메모리가 아닌 CPU 내부의 레지스터 (register)에 할당되는 변수
- 일반 메모리보다 빠르게 참조돼 처리속도가 빠름 : 반복문 횟수 제어변수에 이용하면 효과적
- 시스템 레지스터의 수는 한정되어 있음
=> 레지스터 변수로 선언하더라도 레지스터가 모자라면 일반 지역변수로 할당
- 일반 메모리에 할당되는 변수가 아니므로
주소연산자 &
사용 불가능
cf. 일반변수
- 메모리에 할당
- 연산을 위해 CPU 내부 레지스터를 불러들여 연산 수행
정적 변수
1) 정적 변수란
- 키워드
static
를 자료형 앞에 넣어 선언 - 정적지역변수(static global variable)과 정적전역변수(static local variable)로 나눌 수 있음
- 정적 지역변수 : 함수나 블록에서 정적으로 선언되는 변수
- 정적 전역변수 : 선언된 파일 내부에서만 참조 가능 =>
extern
에 의한 참조 불가능
- 초기 생성된 이후 메모리에서 제거 되지 않음 => 지속적으로 저장 값을 유지하거나 수정가능
- 프로그램이 시작되면 메모리에 할당, 종료되면 메모리에서 제거
- 초기화 : 단 한번만 수행, 상수만 가능
- 초기값 미지정 시
0
,\0
,NULL
값 저장
/* 정적 전역변수 */
//1. 참조범위 : 선언된 파일에만 한정, extern을 이용한 참조가 불가능
//2. 변수의 할당과 제거 : 전역변수의 특징
static int svar = 1;
int main()
{
/* 정적 지역변수 */
//1. 참조범위 : 지역변수 => 선언된 블록 내부에서만 참조 가능
//2. 변수의 할당과 제거 : 전역변수의 특징 => 블록 종료 시에도 메모리에 유지, 관리
static int svar2 = 2;
return 0;
}
#include <stdio.h>
void reset(void);
void coount(void);
int main(void)
{
for(int i = 1; i <= 5; i++)
{
reset(); //1 1 1 1 1
count(); //10 11 12 13 14
}
}
void reset(void)
{
auto int n = 1;
printf("자동지역변수 n : %d", n);
n++;
}
void count(void)
{
static int s = 10;
printf("정적지역변수 S : %d", s);
s++; //이전 값 누적
}
extern 변수
1) extern 변수란
- 새로운 변수를 선언하는 것이 아닌 존재하는 전역변수의 유효범위 확장
extern [자료형] 변수명;
[globalvar.c]
double PI = 3.14;
int main()
{
return 0;
};
[loac1.c]
//유효범위 파일 전체
extern double PI = 3.14;
[loacl2.c]
double hi()
{
//유효범위 함수내부
extern double PI;
...
}
메모리 영역과 변수 이용
메모리 영역
1) 메모리 영역
- 변수의 유효범위(scope)와 생존기간(life time) 결정
데이터(data) 영역
,힙(heap) 영역
,스택(stack) 영역
으로 구분
메모리영역 | 특징 |
---|---|
낮은주소 | - |
데이터영역 | ▫️ 전역변수, 정적변수가 할당되는 공간 ▫️ 먼저 선언되는 변수 순서대로 메모리 주소가 낮은 값에서 높은 값으로 저장장소 할당 ▫️ 프로그램이 시작되는 시점에 정해진 크기대로 고정된 메모리 영역이 확보 |
힙 영역 | ▫️ 동적할당(dynamic allocation)되는 변수가 할당되는 저장공간 ▫️ 프로그램이 실행되면서 영역 크기가 계속적으로 변할 수 있음 ▫️ 데이터 영역과 스택 영역 사이에 위치 ▫️ 메모리가 동적으로 할당 |
스택 | ▫️ 함수 호출에 의한 형색 매개변수, 함수 내부의 지역변수가 할당되는 저장공간 ▫️ 메모리 주소가 큰 값에서 작은 값으로 저장장소 할당 ▫️ 함수호출과 종료에 따라 큰 주소에서 작은 주소로 메모리가 할당되었다가 다시 제거되는 작업이 반복 ▫️ 프로그램이 실행되면서 영역 크기가 계속적으로 변할 수 있음 |
높은주소 | - |
변수 이용
1) 이용기준
- 일반적 : 전역변수의 사용 자제하고 주로 지역변수 이용
- 예외적 : 다음 기준을 따름
- 실행속도 개선 : 레지스터 변수 이용
- 함수나 블록이 종료되어도 값을 저장하고 싶을 때 : 정적 지역변수 이용
- 해당 파일 내부에서만 변수를 공유하고자 하는 경우 : 정적 전역변수 이용
- 프로그램 모든 영역에서 값을 공유 : 전역변수(가능하면 사용을 줄이자)
2) 변수가 정의되는 위치에 따른 분류
선언 위치 | 변수 | 키워드 | 유효범위 | 기억장소 | 생존기간(변수의 할당과 제거시기) |
---|---|---|---|---|---|
전역 | 전역변수 | 참조선언 extern | 프로그램 전역 | 메모리 데이터영역 | 프로그램 실행시간 |
전역 | 정적 전역변수 | static | 파일내부 | 메모리 데이터영역 | 프로그램 실행시간 |
지역 | 정적 지역변수 | static | 함수나 블록내부 | 메모리 데이터 영역 | 함수 또는 블록 실행시간 |
지역 | 레지스터 변수 | register | 함수나 블록내부 | 레지스터 enter code here 변수 | 함수 또는 블록 실행시간 |
지역 | 자동 지역변수 | auto(생략가능) | 함수나 블록내부 | 메모리 데이터 영역 | 함수 또는 블록 실행시간 |
3) 변수의 종류에 따른 생존기간과 유효범위
구분 | 종류 | 메모리 할당 시기 | 동일 파일 외부함수 | 다른 파일 외부함수 | 메모리 제거시기 |
---|---|---|---|---|---|
전역 | 전역변수 | 프로그램 시작 | 이용가능 | 이용가능 | 프로그램 종료 |
전역 | 정적 전역변수 | 프로그램 시작 | 이용가능 | 이용불가능 | 프로그램 종료 |
지역 | 정적 지역변수 | 프로그램 시작 | 이용불가능 | 이용불가능 | 프로그램 종료 |
지역 | 레지스터 변수 | 함수(블록)시작 | 이용불가능 | 이용불가능 | 함수(블록) 종료 |
지역 | 자동 지역변수 | 함수(블록)시작 | 이용불가능 | 이용불가능 | 함수(블록) 종료 |
4) 변수의 초기값
구분 | 종류 | 자동 저장되는 기본 초기값 | 초기값 저장 시기 |
---|---|---|---|
전역 | 전역변수 | 자료형에 따라 0 , '\0' , NULL 저장 | 프로그램 시작 |
전역 | 정적 지역변수 | 자료형에 따라 0 , '\0' , NULL 저장 | 프로그램 시작 |
지역 | 정적 지역변수 | 자료형에 따라 0 , '\0' , NULL 저장 | 함수나 블록이 실행될 때마다 |
지역 | 레지스터 변수 | 쓰레기 값이 저장 | 함수나 블록이 실행될 때마다 |
지역 | 자동 지역변수 | 쓰레기 값이 저장 | 함수나 블록이 실행될 때마다 |