Printf(1)

zeroet·2021년 1월 22일
0

42

목록 보기
2/6

Printf 매개변수 가변인자

printf("%d, %s, %c", 1, str, 'c');

함수 인자의 갯수를 변경해도 문제없이 작동하는 printf함수는 어떤 인자를 갖고있을까?

1. printf 의 원형

int printf(const char* formt, ...)

printf함수의 두번째 인자로 사용되는 ... 이 가변 인자 혹은 가변 파라미터 이다.

가변인자의 함수를 만들기 위해서는 stdarg.h 헤더파일을 포함해야한다. 이 헤더파일에는 가변인자 함수를 만들때 필요한 매크로 들이 정의되어잇다.
가변인자 함수를 만들때에는 최소 1개 이상의 고정인수가있어야 한다. 가변인자 ...은 파라미터 순서상 가장 뒤에 있어야 한다.

#include <stdio.h>
#include <stdarg.h>

int sum(int count, ...)
{
    int res = 0;
    va_list ap;
    int i;

    va_start(ap, count);

    for(i=0; i<count; i++)
        res += va_arg(ap, int);

    va_end(ap);

    return res;
}

int main()
{
    printf("%d\n", sum(10, 1,2,3,4,5,6,7,8,9,10));

    return 0;
}

[출력 결과]
55

가변 인자를 이용해서 모든 파라미터를 더해주는 sum() 함수이다.

  • va_list: 각 가변인자의 시작 주소를 가리킬 포인터, char*로 정의되어있다.

  • va_start: va_list 로 만들어진 포인터에게 가변인자 중 첫번째 인자의 주소를 가르쳐주는 중요한 매크로이다.
    #define va_start(ap,v) ( (ap) = (va_list)_ADRESSOF(v) + _INTSIZEOF(v) )

    • ap: va_list 로만든 포인터가 담긴다.
    • v: 마지막 고정인수가 담긴다.
    • _ADRESOF(v) ==> &(v), 즉 주소로 바꿔주는 매크로
    • _INTSIZEOF(n)=> ((sizeof(n)+sizeof(int) -1) & ~(sizeof(int)-1)), 비트여난이 들어감. 마지막 고정인수의 사이즈를 구해서 그 다음 인자의 시작 주소 즉, 가변인자의 시작주소까지의 메모리상의 거리를 구해주는 매크로.
  • va_arg: 특정 가변인자를 가리키고있는 va_list포인터를 다음 가변인자로 이동 시켜주는 매크로

    • char 형을 사용할때에는 int 를 쓰고 char 로 형변환 시켜줘야 한다 ex) char ch = (char) va_arg(ap, int); - char/short = int // float = double
      이외의 int, long, double 타입은 정상작동
  • va_end : 사용한 가변인자 변수를 끝낼때 사용한다 NULL포인터로 돌려주는 매크로이다.

profile
42 Paris developer

관심 있을 만한 포스트

0개의 댓글