2012-10-01 2 views
0

전 처리기 지시문을 사용하여 C에서 함수 매크로를 정의하고 있습니다. 함수 매크로에서 여러 if/else if 문을 사용할 수 있습니까?전 처리기 다중 if/else if 문을 사용하여 함수 매크로를 정의하는 지시문

예인 경우 어떻게 작성합니까?

#define WRITE(str,id) #str(id) 

// HERES where I am having difficulty 
#define DRAW_GENERIC_WINDOW(windowID, type) if type==1 WRITE(draw_text,windowID) else if type==2 WRITE(draw_image,windowID) else if type==3 WRITE(draw_hyperlink,windowID) 

// usage 
DRAW_GENERIC_WINDOW(112, 1); 
DRAW_GENERIC_WINDOW(178, 2); 
DRAW_GENERIC_WINDOW(988, 3); 

// At compile time the above should be converted to... 
draw_text(112); 
draw_image(178); 
draw_hyperlink(988); 

나는 하나를 수행하는 방법을 알고있는 경우 다른 함수 매크로 문하지만/사람의 경우 경우 여러 방법으로 할 수 있습니다 : 당신은 왜 "하기 전에 :

// if else eg 
#define DRAW_GENERIC_WINDOW(windowID, type) ((type)==(1))?WRITE(draw_text,windowID):WRITE(draw_image,windowID) 

주 도대체 당신이 이런 식으로 프로그래밍하고 있니? " : P는 4dm이라는 C와 매우 비슷한 언어로 작성 되었기 때문에 구조체, 포인터 또는 새로운 데이터 형식을 선언 할 수있는 기능이 없다는 점만 다릅니다. 그래서 가상 함수의 일부 형식을 달성하기 위해 전 처리기 지시문에 의존해야합니다 (이미지, 하이퍼 링크 등의 유형을 모르는 경우 사용됨).

+0

if-else-if-else-if ... 원하는만큼 매크로를 확장 할 수 있어야합니다. 주목 : 나는 DRAW_GENERIC_WINDOW() 확장을 디버깅하는 것이 아니라, 다스 개 이상의 절을 그릴 때 특히 유용합니다. – WhozCraig

+0

파운드 앞에 "#"문자가 나오는 이유는 무엇입니까? #define WRITE (str, id) str (id) #define WRITE (str, id) str (id) – imreal

답변

3

은 다음과 같이 그것을 밖으로 시도 :

#define WRITE(str,id) str(id) 

// HERES where I am having difficulty 
#define DRAW_GENERIC_WINDOW(windowID, type) if (type==1) \ 
WRITE(draw_text,windowID) \ 
else if (type==2) \ 
WRITE(draw_image,windowID) \ 
else if (type==3) \ 
WRITE(draw_hyperlink,windowID) 

// usage 
DRAW_GENERIC_WINDOW(112, 1); 
DRAW_GENERIC_WINDOW(178, 2); 
DRAW_GENERIC_WINDOW(988, 3); 
+0

매크로를'do {...} while 매크로로 둘러 쌉니다. 또는'if' 문에서 사용하면 나쁜 동작을 일으킬 수 있습니다. 그 자체로, 시퀀스'if (something) DRAW_GENERIC_WINDOW (112,1); 'foobar()'는'something'이 true 일 때만 (가끔) 호출 될 것입니다. –

1

그냥 기본 패턴 매칭으로 토큰 붙여 넣기 연산자 ##을 사용하여, 다음과 같이 :

#define DRAW_GENERIC_WINDOW(windowID, type) DRAW_GENERIC_WINDOW_ ## type(windowID) 

#define DRAW_GENERIC_WINDOW_1 draw_text 
#define DRAW_GENERIC_WINDOW_2 draw_image 
#define DRAW_GENERIC_WINDOW_3 draw_hyperlink 

다음과 같이 사용 :

DRAW_GENERIC_WINDOW(112, 1); // expands to draw_text(112, 1); 
DRAW_GENERIC_WINDOW(178, 2); // expands to draw_image(178); 
DRAW_GENERIC_WINDOW(988, 3); // expands to draw_hyperlink(988); 
+0

'type' 매개 변수가 항상 리터럴 숫자 인 경우에만 작동합니다. 'type'이 리터럴 숫자로 확장되는 매크로 인 경우 작동하도록 만들 수 있습니다. 하지만 변수 나 열거 형을 사용하려면 운이 없으면됩니다. 그렇다고 이것이 좋은 해결책이 아니라는 의미는 아닙니다. 한계가 받아 들여 지는지 확인해야합니다. –

관련 문제