2013-08-17 1 views
5

나는 구조체 정의와 같은 :offsetof (member)가 sizeof (struct)와 같은 이유는 무엇입니까?

struct smth 
{ 
    char a; 
    int b[]; 
}; 

나는이 구조체에 sizeofoffsetof 전화 :

cout << sizeof(struct smth) << endl; 
cout << offsetof(struct smth, b) << endl; 

출력은 다음과 같습니다

4 
4 

와서 어떻게 할 때의 크기 stuct가 4이고 char이 1 바이트를 사용하면 int 배열의 오프셋은 4입니까? 왜 어떤 종류의 패딩이 있습니까? 또한, int 배열이 전혀 공간을 차지하지 않는 이유는 무엇입니까?

+1

'offsetof (struct smth, b)'를 의미합니까, 맞습니까? –

+0

@CarlNorum 예, 있습니다. 편집 됨. – bugra

+2

C 또는 C++입니까? 그들은 다르다. –

답변

8

stuct의 크기가 4이고 char이 1 바이트를 사용하면 int 배열의 오프셋은 4일까요? 왜 어떤 종류의 패딩이 있습니까?

C 표준에서 허용하는 패딩이 있습니다. 컴파일러는 종종 성능을 향상시키기 위해 변수를 정렬합니다.

왜 두 번째 변수가 전혀 공백을 차지하지 않는 것입니까?

이것은 C99 유연한 배열 구성원입니다. 그게 전부 요점입니다. 아이디어는처럼 구조 뭔가를 할당하는 것입니다

struct smth *s = malloc(sizeof *s + 10 * sizeof s->b[0]); 

을 그리고 당신은 b은 10 요소의 배열 인 것처럼 작동하는 구조를 가지고 것입니다.

+0

어떤 종류의 성능 향상이 허용합니까? 그냥 궁금해서. – bugra

+0

@ biox6에서 일부 프로세서로드 명령어는 단어 정렬 주소의 단어 만로드 할 수 있습니다. 정렬되지 않은 주소에 단어가있는 경우 각 바이트를 별도로로드하고 다시 결합해야합니다. –

+0

할당 문은 정렬 제약 조건을 고려하지 않습니다. 일반적으로 올바른 양의 메모리를 할당하지 못합니다. 대신에'struct smth * s = malloc (offsetof (struct smth, b [10]));'을 사용하여 적절한 크기의 구조체를 할당 할 것이다. – IInspectable

3

구성원의 크기가 0이기 때문에 컴파일러에서 이 "word"경계에 있도록 과 b 구성원 사이에 패딩을 추가합니다.

그러나 올바르게 올바른 구조체에 유연한 배열이있는 것을 기억한다면 C++이 아니라 컴파일러 확장으로 만 유효합니다.

+0

이 int b []는 int * b와 같습니다. – Light

+2

아니야. 'int * b'는'sizeof (smth)'를 더 크게 만들 것이고 여분의 공간은 int 변수의 주소가 저장 될 곳이 될 것입니다. 대신, int b []는 구조체가 하나의 메모리 블록으로서 정수 (컴파일 타임에 알려지지 않은)의 수를 동적으로 할당해야한다고 말한다. – mity

+0

@mity 변수 b에 값을 어떻게 대입합니까? 할당 문을 줄 수 있습니까? – Light

2

영업 이익은 질문 ++ C라고 코멘트 이후 :

struct smth 
{ 
    char a; 
    int b[]; 
}; 

b[] 같은 배열은 C++에서 유효하지 않습니다. 배열의 크기는 고정되어 있어야합니다. 가변 길이 배열은 C99에서만 유효합니다.

컴파일러에서 확장명을 지원한다고 가정하면 b[] 배열의 크기는 0이므로 struct를 char 구성원으로 만 만듭니다. struct의 패딩 규칙은 컴퓨터에서 4 바이트 인 단어로 struct을 채 웁니다.

관련 문제