MISRA 보면 #, ## 매크로에서 2번쓰지 말라는 규칙이 있다. 그런지 궁금해서 찾아봤다.

 

 

Rule 요구사항과 Justification 영문은 이렇다.

There shall be at most one occurrence of the # or ## operators in a single macro definition

 

Because the evaluation order of # and ## are not specified, the results of using them both in the same macro could be unpredictable. Therefore macros should contain at most once instance of either # or ##.

 

 

해석해보니

"# ## 연산 순서가 지정되어 있지 않기 때문에 동일한 매크로에서 둘다 사용하는 경우에 결과를 정확히 예측할 없기 때문에 # 또는 ## 한번만 포함해야 한다 " 뜻이다.

 

 

[ 오류가 예상되는 예시 ]

#define NonCompliant(a, b)  # a ## b
int main() {
  std::cout << NonCompliant(Hello, World);
}

 

 

코드에서 컴파일러가 2가지 경우를 내보낼 있다.

  1. ## 먼저 연산할 경우 : HelloWorld
  1. # 먼저 연산할 경우 : *Hello "World *

나올 있다.

 

 

[ 규칙을 지킨 예시 ]

 

#define Stringfy(a) #a
#define Compliant(a, b)  Stringfy(a##b)

int main(){
  std::cout << Compliant(Hello, World);
}

 

이 경우에 정확히 HelloWorld 가 프린트 된다

 

[ Reference ]

 

MISRA C 2012, Rule 20.11

MISRA C 2004, Rule 19.12

군대 1개월 다녀오면서 많은걸 느꼈네요. ㅎㅎ

덕분에 블로그에 글 쓰는걸 귀찮아 하지 않고 열심히 쓰려 합니다. 


이번편은 C언어 매크로 편이고, 알아두고 쓰면 좋은 C언어 매크로들입니다. 


좋은점: 매크로를 사용하면 컴파일러에서 처리하기 때문에 실행시간이 줄어드는 효과가 있음.

속도에 민감한 프로그램을 작성한다면 꼭 매크로를 사용하는것이 좋음 실예로, MAX(A,B) 매크로 함수를 사용하여 시간 덕을 보았음


매크로를 앞으로 쭈~~욱 업데이트할 예정임 ㅎ


#define ABS(a)(((a) < (0))?-(a):(a))

#define SWAP(ab)(a)^=(b)^=(a)^=(b)

#define LIMIT(vallh)((val)<(l)?(l):(val)?(h)?(h):(val))


#define SAFE_DELETE(xif(xdelete xx = NULL;

#define SAFE_DELETE_ARRAY(xif(xdelete []xx = NULL;

#define SAFE_RELEASE(xif(xx->Release(); x = NULL;

#define SAFE_DELTE_OBJECT(xif(xDeleteObject(x);


#define IS_ARRAY_ACCESS(varmaxval) (0 <= var && var < maxval) ? true : false

#define IS_VALID_VALUE(varminvalmaxval) (minval <= var && var < maxval ) ? true : false


// 조건문매크로

#define IS_TRUE(c)     (c)

#define IS_FALSE(c)(!(c))


#define IS_EXIST(c)(c)

#define IS_NOT_EXIST(c)(!(c))


#define IS_VALID(c)(c)

#define IS_INVALID(c)(!(c))


// 포인터매크로

#define IS_NULL(p)(!(p))

#define IS_NOT_NULL(p)(p)


// 컴파일러가 지원하는 매크로
__FILE__ //현재 파일을 스트링으로 반환한다

__FUNCTION__ // 현재 함수를 스트링으로 반환한다. __func__를 써야할 경우도 있음.

__LINE__ // 현재 줄을 정수로 반환한다.

ex) printf("%d", __LINE__); 을 하면 이 프린트 라인의 라인수를 출력해준다 


+ Recent posts