2014-10-30 5 views
1

요소가 조건부로 존재하는 C 구조체를 정의하려고합니다.조건부로 요소가있는 구조체 정의

typedef struct flowHeader { 
    int magicNum ; 
    int trafficType ; 
    // few other int parameters 
    int flowDirection; // Present ONLY if trafficType = TT_V6 
    // few other int parameters 
} t_flowHeader ; 

내가이 데이터 유형을 정의하는 가장 좋은 방법 알고 싶어 : 여기 정의 할 헤더의 구체적인 예이다. 이 헤더를 유선상으로 수신되는 버퍼에 적용하고 싶습니다. 한 요소가 없기 때문에 구조의 크기는 4 바이트로 다양하며이를 관리하는 방법에 어려움을 겪고 있습니까?

# define TT_V6 31 
# define FD_NA 0 
int flowDir ; 
unsigned char buf[ MAXSZ ] ; 
t_flowHeader * hdr ; 


hdr = (t_flowHeader *) buf ; 
if (hdr->trafficType == TT_V6) { 
    flowDir = hdr->flowDirection ; 
} else { 
    flowDir = FD_NA ; 
} 

..

+0

역 참조하기 전에 buf에서 4bytes를 재정렬하십시오. –

+0

이것은 옵션이 아닙니다. 어떤 시점에서이 구조를 직렬화해야하는 논리가 있습니다 ... 따라서 순서 변경은 선택 사항이 아닙니다. 또한 그것은 내 머리글을 들어오는 메시지 버퍼에 캐스팅하여 얻는 속도 이점을 완전히 바꿀 것입니다. – user2610390

답변

0

난 당신이 조건의 기본에 구조체의 크기를 변경할 수 있다고 생각하지 마십시오.

  1. 여러 구조를 정의하고 그에 따라>

  2. 그들을 사용하거나 구조의 끝에 조건부 존재하는 것으로 가정되는 이러한 요소를 정의 할 수 있습니다.

0

아니요,이 작업을 수행 할 수 없습니다.

C는 정적 인 언어이므로, 먼저 선언해야합니다. 컴파일러는 프로그램을 실행하기 전에 코드를 생성 할 수 있어야하며, 런타임 요구 사항에 따라 코드를 변경할 수 없습니다.

두 개의 다른 구조체를 선언 한 다음 if 테스트를 사용하여 런타임 데이터를 기반으로 적절한 구조체를 선택해야합니다.

+0

고마워요. 이전 메모에서 썼듯이, 수표가 저에게 잠재적 인 성과 일 경우 한 번 더 ... 저도 그 문제를 피하려고했습니다. – user2610390

1

두 가지 유형을 사용하는 것이 한 가지 방법입니다. 당신은 다른 공유 구성 요소의 모든 중첩 된 유형을 정의하여 중복을 줄일 수

struct flowHeader_start { 
    int magicNum ; 
    int trafficType ; 
    // few other int parameters 
}; 

struct flowHeader_end { 
    // few other int parameters 
}; 

typedef struct flowHeaderA { 
    struct flowHeader_start s; 
    int flowDirection; // Present ONLY if trafficType = TT_V6 
    struct flowHeader_end e; 
} t_flowHeaderA ; 

typedef struct flowHeaderB { 
    struct flowHeader_start s; struct flowHeader_end e; 
} t_flowHeaderB ; 

... 조금 캐스트 다음 다시 정렬 :

if (((struct flowHeader_start *)buf)->trafficType == TT_V6) { 
    hdr = (t_flowHeaderA *) buf ; 
    flowDir = hdr->flowDirection ; 
} else { 
    hdr = (t_flowHeaderB *) buf ; 
    flowDir = FD_NA ; 
} 

유형 자체가 조건에 의존하지를 두 가지 가능한 유형이 각각 인 경우이 사용됩니다.

struct flowHeader_start의 끝 부분까지의 두 유형의 구조는 정확히 동일해야합니다 (동일한 첫 번째 요소가 있고 구조체는 첫 번째 요소에서 패딩하지 않아야하기 때문에). 따라서 캐스트 할 수 있습니다. 어느 한 유형과 struct flowHeader_start 사이에 안전하게 저장됩니다. 즉, 나머지 버퍼의 형태를 알지 못해도 첫 번째 블록 내에 배치 된 조건을 테스트 할 수 있습니다.

확장자에 따라 일부 컴파일러에서는 중첩 된 구조체를 익명으로 만들 수 있습니다. 더보기 쉽고 마지막 구조체의 요소에 중간 필드를 통해 액세스하지 않아도됩니다. 표준은 이것을 명명 된 타입들에 허용한다.)

+0

이것은 실제로 제가 생각한 옵션 중 하나였습니다. 여러분이 올바르게 지적했듯이 - 이것은 하나 더 확인을 필요로합니다 -이 코드는 패스트 패스에 있습니다 - 나는 작은 퍼포먼스를가집니다. 나는이 형벌을 피하려고했다. – user2610390

+0

? 여기에는 질문의 코드와 똑같은 하나의 수표가 포함됩니다. – Leushenko