2011년7월5일_함수를 반환하는 함수와 함수를 반환하는 함수의 함수포인터

 

★ 기초를 다진 후에 기본을 탄탄히 한 다음에 기교를 부려라.
    고급기술을 배우기 위해선 기본이 되어 있어야 함.
    끝임없는 기초수련을 통해 단련된 두뇌에서 멋진 기술이 나올거야…

 

● printf()를 반환하는 test( )

   1:  //printf( )를 반환하는 test( )의 원형을 구하는 과정
   2:  //0.test( )의 원형 중 인자만 표시
   3:  test(void)
   4:  //1.printf( )의 원형
   5:  int printf(const char *,...);
   6:  //2.printf( )의 원형에서 이름을 *로 대치
   7:  int (*)(const char *,...);
   8:  //3.test( )의 앞에 *부터 왼쪽부분 갖다 붙임
   9:  int (*test(void)
  10:  //4.test( )의 뒤에 *다음 부분을 갖다 붙이면 완성
  11:  int (*test(void))(const char *,...);








오늘의 연습문제

 

   1:  #include <stdio.h>
   2:  //test1 선언(인수 1개, float f)
   3:  //test2 선언(인수 1개, char c)
   4:   
   5:  int main()
   6:  {
   7:    int (*fp)(const char *, ...)=0;
   8:    //fp1 선언
   9:    //fp2 선언
  10:   
  11:    fp2 = test2;
  12:    fp1 = fp2('a');
  13:    fp  = fp1(0.1);
  14:   
  15:    fp("Hi....\n");
  16:    return 0;
  17:  }
  18:   
  19:  //test1 정의(인수 1개, float f)
  20:  {
  21:    printf("float : %0.1f\n", f);
  22:    return printf;
  23:  }
  24:   
  25:  //test2 정의(인수 1개, char c)
  26:  {
  27:    printf("char : %c\n", c);
  28:    return test1;
  29:  }
  30:   
  31:   


주석처리된 부분을 완성하라~

 


● printf( )를 반환하는 test( )를 가리킬 수 있는 함수포인터 fp1

   1:  //test1( )의 원형을 구하고 함수포인터를 구하는 과정
   2:  //0.test1( )의 원형 중 인자만 표시
   3:  test1(float f)
   4:  //1.printf( )의 원형
   5:  int printf(const char *,...);
   6:  //2.printf( )의 원형에서 이름을 *로 대치
   7:  int (*)(const char *,...);
   8:  //3.test1( )의 앞에 *부터 왼쪽부분 갖다 붙임
   9:  int (*test1(float f)
  10:  //4.test1( )의 뒤에 *다음 부분을 갖다 붙이면 test1( )의 원형이 완성됨.
  11:  int (*test1(float f))(const char *,...);
  12:   
  13:  //5.함수포인터fp1을 구하기 위해 test1( )의 이름을 (*)로 바꿈.
  14:  int (*(*)(float f))(const char *,...);
  15:  //6.(*)에서 *다음에 함수포인터의 이름을 삽입하면 함수포인터fp1완성
  16:  int (*(*fp1)(float f))(const char *,...);
  17:   

 

● test1( )을 반환하는 test2( )를 가리킬 수 있는 함수포인터 fp2 (복잡함)

   1:  //test1( )의 원형에서 test2( )의 원형을 구하고 함수포인터를 구하는 과정
   2:  //0. test1( )의 원형
   3:  int (*test1(float f))(const char *,...);
   4:  //1. test2( )의 원형 중 인자만
   5:  test2(char c)
   6:  //2. test1( )의 이름을 (*)로 대치하고 인자명 삭제
   7:  int (*(*)(float))(const char *,...)
   8:  //3. test2( )의 앞에 *부터 왼쪽부분을 갖다 붙임
   9:  int (*(*test2(char c)
  10:  //4. test2( )의 뒤에 *다음 부분을 갖다 붙이면 test2( )의 원형 완성
  11:  int (*(*test2(char c))(float))(const char *,...);
  12:   
  13:  //5. 함수포인터 fp2를 구하기 위해 test2( )의 이름을 (*)로 바꿈.
  14:  int (*(*(*)(char c))(float))(const char *,...);
  15:  //6. (*)에서 *다음에 함수포인터의 이름을 삽입하면 함수포인터 fp2완성
  16:  int (*(*(*fp2)(char c))(float))(const char *,...);

 

 

● 답

   1:  #include <stdio.h>
   2:   
   3:  //test1()
   4:  int (*test1(float))(const char *,...);
   5:  //test2()
   6:  int (*(*test2(char))(float))(const char *,...);
   7:   
   8:  int main()
   9:  {
  10:      //int printf(const char *, ...);
  11:      int (*fp)(const char *, ...) = 0;
  12:      
  13:      //fp1 선언
  14:      //int (*test1(float))(const char *,...);    //test1()의 원형 test1 -> *fp1
  15:      int (*(*fp1)(float))(const char *,...) = 0;
  16:      //fp2 선언
  17:      int (*(*(*fp2)(char))(float))(const char *,...) = 0;
  18:   
  19:      fp2 = test2;        //test2( )의 프로토타입에 맞춰 fp2선언
  20:      fp1 = fp2('a');        //test2( )반환함수인 test1( )의 프로토타입에 맞춰 fp1선언해야됨
  21:      fp  = fp1(0.1);        //fp는 test1()의 반환함수인 printf()형과 같은 함수포인터
  22:   
  23:      fp("Hi....\n");
  24:      
  25:      return 0;
  26:  }
  27:   
  28:  //test1 정의(인수 1개, float f)
  29:  int (*test1(float f))(const char *,...)
  30:  {
  31:    printf("float : %0.1f\n", f);
  32:    return printf;
  33:  }
  34:   
  35:  //test2 정의(인수 1개, char c)
  36:  int (*(*test2(char c))(float))(const char *,...)
  37:  {
  38:    printf("char : %c\n", c);
  39:    return test1;
  40:  }

 

함수를 반환하는 함수와 그 리턴값을 받는 함수포인터…
이들을 어디에 쓰면 좋을까?
복잡한 응용 소스코드에 적용하면 코드사이즈가 줄어들 것 같으나…실제 적용하려니 막상 떠오르지 않는다.