Team Curio

비주얼 노벨 한국어 패치 팀 큐리오

프로그래밍

5.c 언어강좌 (2)

연이v 2009. 7. 3. 18:35
반응형
SMALL

 ==========================================================================
C 프로그래밍 2회
==========================================================================
저번 강좌 에서는 C프로그램의 기본적인 구조를 이해하셨으리라 봄니다.
이번 강좌 에서는 C프로그램의 구조를 좀더 자세히 살펴보도록 하겠습니다.

1. C 프로그램의 구성 요소
C프로그램을 구성하는 요소들에 대해 알아보도록 하죠.
C프로그램을 구성하는 요소에는 키워드, 심볼, 문장, 블럭등이 있습니다.

(1) 키워드
키워드는 저번 강의때 간략히 설명을 했었는데, 더 정확히 말하자면.. C 컴파일러가 특별한 의미로 인식하는 단어를 말합니다. 다른 단어들과는 달리 특별한 기능을 수행하게 되죠. C언어 키워드는 다른 언어에 비해 적은 편 입니다. 이유는 C언어 키워드에는 표준 입출력에 관한 키워드가 들어있지 않기 때문이죠. 단지 데이터 처리와 프로그램의 흐름을 제어하는 키워드 밖에 들어있지 않습니다. 그렇기 때문에.. 표준 입출력에 관한 것은 외부에 의존합니다. 저번히 예제에 나온 printf라는 것도 키워드가 아님니다. 이것이 무엇인지는 오늘 배우게 됨니다.

(2) 심볼
심볼은 무언가를 상징하는 단어로 키워드와는 반대의 의미를 가지는 단어라고 할수 있습니다. 즉 이건 컴파일러가 특별한 의미로 인식하는 단어가 아닌 프로그램을 만드는 사람이 특별한 의미를 부여하는 단어 입니다. 키워드와는 다르게 프로그램을 만드는 사람이 특별한 기능을 수행하도록 만들게 되죠. 이 심볼에 해당하는 것은 오늘 배울 변수와 함수 이름등이 있습니다. 심볼은 한개 이상의 문자로 만들수 있으며 이때 사용할수 있는 문자는 알파벳과, 숫자, 언더 스코어('_')가 있습니다. 그런데 멘 처음 문자는 반드시 알파벳 또는 언더스코어가 와야 합니다. 예를 들자면.. symbol, _symbol, symbol1 이런것들은 심볼이 될수 있지만.. 1symbol, 2symbol 이런건 에러가 나게 됨니다..

(3) 문장
문장은 프로그램을 구성하는 중요한 요소로 실행 단위가 된다고 할수 있습니다. 문장에는.. a=b+c; printf("Example"); 이런 것들이 있으며, 문장 이 끝나면 반드시 ';'를 써 주어야 합니다. ;이 문장의 끝을 알리는 표시 이죠.

(4) 블럭
블럭은 문장을 묶어 둔 것 입니다. 즉 한개 이상의 문장이 모여 있는 것을 말하죠. 블럭은 {로 시작해 }로 끝남니다. 예를들어.. { a=b+c; b=a+c; } 이건 블럭이라 할수 있습니다. 그리고 블럭은 중첩될수도 있습니다. { a=b+c; { b=a+c; } } 이런 식으로 말입니다.

2. C 프로그램의 구조.
예제 소스를 하나 보며 공부하도록 하죠.
/* 파일 이름 : C2-1.C
프로그램 내용 : 계산에 대한 결과를 출력하는 프로그램*/

#include int add(int,int); /* 두 수를 더하는 함수 */
void main() { int result; /* 변수 선언 */
result=add(3,5); /* add함수를 호출해 3과 5를 더한다.*/
printf("Result:%d\n",result); /* result의 값을 출력한다. */
} int add(int a, int b) { return(a+b); /* a와 b를 더해서 리턴 */}

이 프로그램은 아주 간단하지만 처음 하시는 분은 좀 복잡해 보일 겁니다.
우선 저번 강좌 내용을 들춰 보면서 그때 나온 소스들과 이 소스를 비교해 보세요.
이 소스와 저번 강좌에 나왔던 여러 소스를 비교해 보면 공통점이 몇 가지 있을 것 입니다.
우선 프로그램 처음에 #include 라는 것이 꼭 있고 void main()이라는 것이 어느 소스에나 있을 겁니다. 이것들이 왜 공통적으로 들어 있는지 소스 분석을 통해 알아보죠.

(1) 선행처리기 지시어.
여기서 한 줄씩 살펴보기로 하죠.
우선 처음에는 #include 이런 문장이 있습니다. 이 문장처럼 #가 붙은 것을 선행처리기 지시어라고 합니다. 저번 강의때 들은적이 있으실 겁니다. 이 선행처리기 지시어는 메크로 기능, 파일 포함 기능, 선택적 컴파일 기능등 여러 기능을 수행합니다. 그중 여기 나온 #include라는 지시어는 지정된 파일을 프로그램 내에 포함시키라는 지시어 입니다. 그러니까 위와 같은 경우 stdio.h라는 파일을 프로그램 내에 포함시키라는 것이죠. 자세한 사용법을 살펴보면 #include <포함할 파일> #include "포함할 파일" 이렇게 두가지 형식이 있습니다. 처음 방법은 지정된 디렉토리에서 파일을 찾아 포함시키는 것 입니다. 지정된 디렉토리는 흔히 개발 도구의 INCLUDE디렉토리를 가르키는 것으로 그 안에 들어 있는 파일은 개발 도구를 만든 곳에서 지원하는 것 들입니다. 두번째 방법은 현제 위치한 디렉토리에서 파일을 찾아 포함시키는 것 입니다. 예를들어 현제 디렉토리의 a.h라는 파일이 있는데, 그걸 포함시키고 싶다면. #include "a.h" 이렇게 하면 됨니다. 대부분의 프로그램에서 stdio.h라는 파일을 포함시키는 이유는 차차 배우게 될 것입니다.

(2) 함수와 main함수
두번째 줄은 일단 넘어가기로 하고 다음을 보면

void main() { int result; /* 변수 선언 */
result=add(3,5); /* add함수를 호출해 3과 5를 더한다. */
printf("Result:%d\n",result); /* result의 값을 출력한다. */}

이것이 있습니다.
이렇게 생긴 것들을 함수라고 하는데 함수란 어떤 내용을 처리하고 그 결과를 리턴하는 프로그램의 한 부분입니다.
반드시 하나의 블럭으로 되어 있어야 하죠. 그리고 그 안에는 그 함수가 처리할 내용이 들어가게 됨니다. 함수는 다음과 같은 구조로 만듬니다.

리턴형태 함수이름([인수, 인수, 인수...]) { /* 프로그램 내용 */ . . }

여기서 리턴형태이란 처리하고 난 후의 리턴할 결과의 형태가 무엇인지를 쓰는 것 입니다.
즉 정수형태인지, 문자열인지 등등.. 결과를 리턴하지 않는 경우 void를 씀니다.
함수 이름은 그 함수를 상징하는 심볼 이죠.
인수는 그 함수가 어떤 내용을 처리할때 필요해서 전달받아야 할 데이터 입니다.
예를 들어 화면에 무언가를 출력하는 함수를 만든다고 합시다. 출력하기 위해선 출력할 내용을 전달받아야 하는데 그때 인수를 통해 전달받게 됨니다. 전달받을 데이터가 없으면 안써도 됨니다.
우선 지금 나온 함수는 main이라는 함수인데 이 함수는 어떤 프로그램이든지 존제하고 있었죠?
왜 그럴까요????????????????????
이유는 C언어 프로그램은 바로 main함수에서 시작하게 되기 때문이죠.
C프로그램의 실행되면 이 main함수를 시작으로 프로그램이 진행되고
main함수가 끝나면 프로그램도 끝나게 됨니다.
그러므로 반드시 만들어야할 함수 입니다.
main함수안에 나오는 것을 하나씩 분석해 보면.

int result; /* 변수 선언 */

처음에 이게 나오는데..
이건 변수를 선언하는 것 입니다.
그냥 어떤 값을 저장하기 위해 기억장소를 마련하는 것이라 생각하시면 됨니다.
다음줄은

result=add(3,5); /* add함수를 호출해 3과 5를 더한다. */

이것인데.. 이것은 바로 함수를 호출하는 것 입니다.
그리고 나서 그 결과를 result라는 기억장소에 보관하라는 뜻이죠.
그러니까 지정한 함수 내에 처리 내용을 실행시키고
그때 나온 결과를 result라는 변수에 보관하는 문장입니다.
함수 호출법은 다음과 같습니다.

[변수=]함수이름([인수,인수,인수..]);

여기서 변수는 함수의 내용이 처리된 후 리턴하는 결과를 넣을 기억장소를 말합니다.
결과를 리턴하지 않으면 쓰지 않아도 됨니다. 또한 리턴한 결과를 따로 저장할 필요가 없을때도 쓰지 않아도 됩니다.
그리고 함수이름은 호출할 함수를 상징하는 심볼, 인수는 함수가 하는 처리에 필요한 데이터입니다.
함수를 호출할 때는 그 함수가 만들어져 있어야 합니다. 그리고 함수가 호출하려는 곳보다 밑에 만들어 져 있으면 좋지 않죠.
이유는 위에서는 함수가 있는지를 모르거든요. 그런데 여기선 add라는 함수가 밑에 있죠?
이럴땐 함수를 위에 선언해 주면 좋습니다.
함수가 있다는 것을 알려주는 것이죠.
꼭 그래야 하는 건 아니지만, 요즘 컴파일러들은 경고를 주게 되죠.
그래서 add함수를 선언한 것이 main함수 위에 있는 것인

int add(int,int); /* 두 수를 더하는 함수 */

이거 입니다.
함수 선언은 간단한데.. 리턴형 함수이름([인수, 인수, 인수...]); 이렇게 하면 됨니다.
이것들이 무슨 뜻 인지는 다 아시겠죠? 이렇게 함수를 선언한것을 C에서는 프로토타입을 선언한다고 합니다.
이렇게 프로토타입을 선언하면 에러가 방지되는 등의 좋은 점이 있으므로 프로토타입을 선언하는 습관을 기르는 것이 좋습니다.
이제 add를 호출했으니 add내의 내용을 살펴보죠 add함수를 보면

int add(int a, int b) { return(a+b); /* a와 b를 더해서 리턴 */ }

이렇게 되어 있습니다.
우선 리턴하는 결과는 정수입니다.
int가 정수를 의미하거든요.
int와 같은 것에 대해서는 다음 강좌때 배움니다.
그리고 인수는 a, b두개인데, 아까 result=add(3,5); 이렇게 호출했으므로 a에는 3이, b에는 5가 각각 들어갑니다.
그리고 다음줄은

return(a+b); /* a와 b를 더해서 리턴 */

이것인데.. 이건 함수의 처리를 끝내고 함수를 빠져 나오라는 것 입니다. 또한 함수를 빠져 나올때 a와 b를 더해서 결과로 리턴하라는 것이죠. 여기에 쓰인 return은 이렇게 함수를 빠져 나올때 쓰입니다.
사용법은

return [리턴값];

이때 리턴값이란 결과로 리턴을 해 줄 값을 말합니다. 예를들어 3을 리턴해 주려고 한다면.

return 3;

이렇게 써 주면 됨니다.. 그리고 리턴값을 (와 )로 묶어주면 더 좋겠죠?

return(3);

이렇게.. 특히 리턴값이 식으로 표현될때는 묶어주는 습과을 기르도록 하세요..

return(a+5);

이렇게 말이에요. 만약 함수가 아무 값도 리턴을 하지 않는다면, 리턴값은 생략해도 됨니다. add함수가 3+5를 더한 값인 8을 결과로 리턴하겠네요? 그리고 리턴을 했으니 다시 main함수로 돌아와야 겠죠?
이때 아까

result=add(3,5);

이렇게 호출했으므로 result에는 8이 들어가겠군요. 그럼 다음줄을 볼까요.

printf("Result:%d\n",result); /* result의 값을 출력한다. */

이것 역시 함수를 호출하는 건데.. result값을 화면에 표시하는 기능을 하는 것 입니다.
그런데 좀 이상한게 있지 않나요?? printf라는 함수는 만들지도 않았는데 어떻게 호출했을까요??
그리고 선언 조차도 되어 있지 않죠? 이 함수는 바로 stdio.h라는 파일에 선언되어 있습니다.
stdio.h파일을 포함하는 이유가 바로 이것 때문이죠.
물론 선언을 하지 않아도 상관 없지만 말입니다. 그런데 이 함수를 선언했다 해도 실제 함수가 만들어져 있지 않죠? 이 함수는 C언어 개발 패키지를 만든 곳에서 지원하는 함수로 그곳에서 만들어 컴파일해서 목적 파일로 만든 후 기타 다른 함수들의 목적 파일과 같이 하나의 파일로 묶여 있습니다.
이렇게 목적 파일 한개 이상을 묵은 것을 라이브러리 라고 하고 확장자는 .LIB가 됨니다.
저번 강의때 들은적이 있죠? 라이브러리란 말을.. 그리고 저번 강의때 나온 런타임 라이브러리가 바로 printf함수가 들어있는 라이브러리로 이런 이유때문에 링크시에 런타임 라이브러리가 합쳐지는 것이죠. 런타임 라이브러리가 없으면 printf라는 함수를 쓰지 못하게 되거든요.
이렇게 해서 main함수가 끝났네요 그럼 프로그램이 종료되게 됨니다.
이제 프로그램의 결과를 보기로 하죠. 분석한게 맞았다면 결과가 8이 되겠죠?

C:\>C2-1.EXE
Result:8
C:\>

역시 맞군요..

(3) 다시한번 정리..
이제 간단히 C프로그램의 구조를 정리해보겠습니다.
C프로그램은 기본적으로 다음과 같은 구조로 되어 있습니다.

1. 선행처리기 지시어 부분.
2. 전역 데이터 및 함수 선언 부분.
3. 함수 부분.

처음으로 선행처리기 지시어 부분은 말 그대로 선행처리기 지시어들을 쓰는 부분입니다.
#include외에 여러가지 지시어들은 나중에 배우게 됨니다.
그리고 선행처리기 지시어는 반드시 #로 시작한다는 것을 기억하세요.
두번째 부분은 전역 변수 및 함수 선언 부분 인데 전역 데이터를 선언하거나 함수를 선언하는 곳 입니다. 전역 데이터란 모든 함수에서 사용할수 있는 데이터를 말하는 것으로 다음에 자세히 배움니다.
그리고 함수 선언은 무엇인지 배우셨고...
세번째 부분은 함수 부분 인데 실제적인 프로그램을 기술하는 곳으로서 가장 중요하다고 볼수 있죠.
특히 main함수는 반드시 만들어야 한다는 것을 잊지 마시기 바람니다.
마지막으로 두번째부분은 다른 파일에 따로 기술하여 #include지시어를 통해 포함시키기도 하는데 이때 그 다른 파일을 헤더(앞부분이기 때문)파일이라고 하고 확장자는 .H입니다 그리고 stdio.h도 헤더파일 입니다. 이번 강좌에서는 C 프로그램의 구조를 비교적 자세히 알아보았습니다.
다음 강좌에서는 데이터에 대한 공부를 하겠습니다.
반응형