본문 바로가기
Algorithm/유용한 팁 (Tips)

[C,C++] 지역변수와 전역변수 특징,백준 1463번 1로 만들기 풀이

by matters_ 2019. 3. 11.

문제 링크

백준 1463번 1로 만들기

 

1463번: 1로 만들기

첫째 줄에 1보다 크거나 같고, 106보다 작거나 같은 정수 N이 주어진다.

www.acmicpc.net

 

1로 만들기는 지난번에 풀이한 적이 있지만 한번 복습하는겸 다시 풀기로 했다.
C언어 문법으로 갈아타고 여기저기 주운 지식을 이용해 다시 코드를 작성하니 확실히 깔끔해졌다.
또한 유명코더분들이 배열을 만들때 전역변수로 만드는 경우가 많았는데
오늘 이문제를 다시 풀어보며 차이점을 포스팅하기로 했다. 

 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
#include <cstdio>
int n,dp[1000001];
int main(){    
    scanf("%d",&n);
    for(int i=0;i<=n;i++)dp[i]=0x3ffffff;
    dp[1]=0;
    for(int i=2;i<=n;i++){
        if(i%2==0)dp[i]>dp[i/2]+1?dp[i]=dp[i/2]+1:dp[i];
        if(i%3==0)dp[i]>dp[i/3]+1?dp[i]=dp[i/3]+1:dp[i];
        dp[i]>dp[i-1]+1?dp[i]=dp[i-1]+1:dp[i];    
    }
    printf("%d",dp[n]);
}
cs

▲ 새로 작성한 C코드 

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#include <iostream>
#include <vector>
#include <limits.h>
using namespace std;
 
int main(){
    int num;
    cin>>num;
    vector <int> DP(num+1,0);
 
    DP[1]=0;
    DP[2]=1;
    DP[3]=1;
 
    for(int i=4;i<num+1;i++){
 
        int candid2=INT_MAX,candid3=INT_MAX;
 
        if(i%2==0)candid2=DP[i/2]+1;
        if(i%3==0)candid3=DP[i/3]+1;
 
        DP[i]=DP[i-1]+1;
        (candid2>=candid3?candid3:candid2)>=DP[i]?DP[i]:DP[i]=candid2>=candid3?candid3:candid2;
    }
    std::cout<<DP[num];
    return 0;
}
 
cs

▲ 지난번 작성한 C++코드

 

여기서 이번에 작성한 코드에서는 dp배열을 main문 안에 넣으니 dev C++에서 실행오류가 발생했는데(지역변수) main문 밖에 선언을 하니(전역변수) 오류없이 잘 돌아가는게 궁금해서 찾아보았다.

 

 

1. 우선 위에서도 언급했듯이 변수의 선언 위치에 차이점이 있다. 전역변수는 함수 밖, 지역변수는 함수 내에서만 사용가능하다. 

 

2. 변수가 사용할 수 있는 사용 범가 다르다. 전역 변수는 선언된 함수 내에서만 사용할 수 있는 지역변수로 달리 프로그램 어디든지 변수를 사용할 수 있다. 지역변수는 함수의 블록을 벗어나버리면 사용이 불가능하다.

 

3. 변수의 생성제시기가 다르다. 변수는 생성시 컴퓨터의 메모리를 할당받고 삭제시 메모리를 다시 시스템에 내어준다. 전역변수는 프로그램의 모든 함수내에서 사용가능해야 하므로 프로그램이 실행 직후 생성되어 프로그램이 종료될 때 삭제된다.

지역변수는 함수 실행시에 생성되고 해당 함수가 끝나면 삭제된다. 해당 함수가 여러 번 실행된다면 여러번 생성삭제된다. 즉, 전역변수는 프로그램생성과 생성삭제시기가 같고 지역변수는 선언된 함수와 생성삭제시기가 같다고 생각하면 된다.

 

4. 다음 이유가 에러가 발생한 중요한 이유라고 생각이 들었다. 컴퓨터에서 저장되는 기억장소가 다르다는 점이다. 전역변수는 한번 생성된 메모리에 남아 있어야 하므로 정적데이터영역에 생성되는 반면 지역변수는 stack(스텍)에 생성된다. 내 코드가 실행오류가 나는 이유는 스텍의 최대메모리 제한 때문인 듯 하다. 리눅스에서 최대 스텍 size는 8MB이고 윈도우에서 비주얼스튜디오를 사용하는 경우 1MB이다. (더 늘일 수 있긴하다.) 아래 참고자료를 보고 참고하자.

 

조금 더 찾아보니 PS할 때는 아주 큰 배열 같은 경우 지역변수보다 전역변수로 선언하는것이 실행시간도 차이가 있다고 한다.

https://www.acmicpc.net/board/view/5437 

https://www.acmicpc.net/board/view/2307

 

5. 마지막으로 초기화 다르다. 전역변수는 초기화를 지정해지주 않아도 0으로 초기화 되나 지역변수는 지정해주지 않으면 쓰레기값이 할당된다. 

 

개발할 때는 주의해서 지역변수를 사용해야하나 PS경우에는 여러측면에서 전역변수가 유리한 듯하다. 

 

 

댓글