printf("정수? %d, 문자열? %s", 5, "문자열이긔");
인자가 3개네요.
printf("실수? %f, 문자열? %s, 정수? %d", 3.14, "문자열이긔", 7);
이번엔 또 인자가 4개군요.
C언어에서는 함수의 오버로딩을 지원 하지 않습니다.
결국 원형은 하나라는 건데..
그럼 printf()함수는 원형이 어떻게 생겼을까요?
#include <stdio.h>
비밀은 여기에 있습니다.
우리가 printf 함수를 쓰면서 당연히 인클루드 하던 stdio.h
이 파일 열어 보신 분 있으신가요?
자 한번 열어서 printf()함수를 찾아 봅시다.
_Check_return_opt_ _CRTIMP int __cdecl printf(_In_z_ _Printf_format_string_ const char * _Format, ...);
웁스;;
이건 암호도 아니고;;;; 별 도움이 않되겠네요;;
오히려 헷갈리는 -ㅁ-;;
그럼 모르는 것 빼버리고 우리가 알고 있는 함수 처럼 만들어 봅시다.
int printf(const char * _Format, ...);
그래도 모르는게 하나 남았네요.
...
장난 하나요? 무슨 쓰기 싫어서 ... 으로 생략 했나 봅니다.
는 아니고 사실 비밀은 저 ...에 있습니다.
우리가 아는 그대로 나머지 인자는 여러개가 있을 수 있다는 이야기 입니다.
아하 그럼 우리도 함수를 저렇게 선언하면 가변적인 인자에도 대응 할 수 있겠군요?
네 그렇습니다.
자 함수 하나 만들어 보죠~
그전에 메인 함수 부터 만들어 보죠.
int main()
{
vaFunc(3, "Hello", "World", "!!!");
return 0;
}
vaFunc() 라는 함수가 가변적으로 인자를 받는 함수입니다.
그럼 선언은
int vaFunc(int argc, ...)
뭐 이렇게 하면 되겠죠?
다음 vaFunc() 함수의 몸체를 써내려가야 하는데...
argc는 쓸 수 있는데 그 다음 부터는 어떻게 하죠?
자 여기서 쓰는것이 va_list 라는 것입니다.
va_list 및 가변 인자에 관한 것은 <stdarg.h> 파일에 정의 되어 있습니다.
#include <stdarg.h>
하시고,
int vaFunc(int argc, ...)
{
va_list argptr;
char *strTemp;
int i;
va_start(argptr, argc);
for(i = 0; i < argc; ++i)
{
strTemp = va_arg(argptr, char *);
printf("Arg %d = %s\n", i, strTemp);
}
va_end(argptr);
return 0;
}
내용물을 체웁시다.
눈썰미 있는 분은 코드만 봐도 아시겠네요.
먼저
va_list argptr;
가변인자를 처리하기 변수를 선언 합니다.
va_start(argptr, argc);
다음으로 가변인자가 시작될 위치를 지정하죠.
우리가 만든 함수와 printf() 는 고정 부분이 하나지만
여러개가 올 수도 있답니다.
vaFunx(int arg1, float arg2, ...);
등으로 말이죠.
위의 경우는
va_start(argptr, arg2);
로 해줘야 합니다.
가변인자는 arg2 다음에 오니 말이죠 ㅎㅎ
strTemp = va_arg(argptr, char *);
가변인자의 인자를 하나씩 strTemp 에 대입해 줍니다.
"Hello", "World", "!!!" 순으로 말이죠.
눈치 체신분도 있으실텐데...
가변인자는 인자의 갯수를 알 수 있는 수단을 제공해야 합니다.
그래서 처음 인자를 뒤의 인자의 갯수로 써주는 것입니다.
그럼 printf()의 경우는??
printf("Arg %d = %s\n", i, strTemp);
를 보시면 삘이 확 오시나요?
그렇습니다.
%d, %s 이런것을 보면 뒤에 오는 인자의 갯수를 알 수 있답니다.
조심해야 할점은 뒤의 인자의 갯수는 모자라면 않된다는 점입니다.
메모리 접근 위반이 나겠죠?
또한 인자의 타입도 달라서는 않됩니다.
마지막으로
va_end(argptr);
내부적으로 초기화를 수행해 완료 작업을 합니다.
메모리 누수가 발생할 수도 있으니 빼먹지 맙시다.
이것으로 우리도 가변인자를 지원하는 함수를 만들 수 있겠네요~
댓글 없음:
댓글 쓰기