2010-12-31 3 views
6

char c[99] = {'Stack Overflow'};을 C 또는 C++로 작성한다고 가정 해 보겠습니다. 그것은 잘 컴파일하지만 이것은 유효합니까? 유효 함으로 어떤 종류의 정의되지 않은 또는 지정되지 않은 동작을 호출하지 않는다는 의미였습니다.유효한 C 문입니까?

다시 말해서 char c[99] = 'Stack Overflow'; gcc를 쓰면 gcc가 멀티 커터 상수에 대해 불평하지만 분명히 위의 경우 중괄호 안에 넣을 때 컴파일러가 행복합니다! 왜 그래야만하지?

첫 번째 문 다음에 puts(c);Stack Overflow 인 일반 문자열의 마지막 문자 바로 'w'를 출력합니다. 왜 그렇게?

누군가 이러한 행동을 별도로 설명 할 수 있습니까?

+3

컴파일하여 알아보십시오. – Falmarri

+5

그는 이미 그것을 컴파일했다고 말했다. – indiv

+22

@Falmarri : 나는 당신이 RTFQ 상을 획득했다고 생각한다. 그는 "그것이 잘 컴파일"하고 출력을 설명하고, 분명히 테스트를 수행했다. 그러나 테스트는 이식성이 있는지 또는 표준에 의해 잘 정의되어 있는지 여부를 알려주지 않습니다. –

답변

14

둘 다 하나의 리터럴이므로 c[0]이 리터럴로 설정되고 c[1] ... c[98]은 0으로 채워집니다 (NUL 문자).

실제로 어떤 값이 c[0]에 들어가는지는 구현에 따라 다르지만 모든 호환 컴파일러에서 컴파일해야합니다.

EDIT는 : C++ 0X의 표준에 대해 적어도 검증 :

위해 다중 리터럴 int와 구현 정의 값을 입력 갖는다.

그리고 C99의

는 (무료 원인, the draft 사용) :

정수 문자 이상의 문자를 포함하는 상수 (예를 들면, 'ab'), 또는 문자를 포함하거나 이스케이프 시퀀스의 값 단일 바이트 실행 문자로 매핑되지 않는 코드는 구현으로 정의됩니다.

+1

+1 멀티 - 렉터 리터럴의 세계에 오신 것을 환영합니다 –

+0

하지만 왜 중괄호를 사용하는 문이 컴파일러의 구문 검사를 통과합니까? – Quixotic

+1

@Philando : 왜냐하면 " compound initializer "는 배열을 초기화하는데 사용 되는가? 완벽하게 합법적이다. 복합 initializer가 하나 이상의 요소를 가져야한다는 규칙은 없다. 사실 int [10] = {0};과 같은 것들이 매우 일반적이다 –

1

동의 - Windows 커널 코드에서 - 많은 태깅 메모리를 볼 수 있습니다. 실제로 플랫폼별로 구현됩니다. 그러나 그들은 ULONG을 사용하여 메모리에 태그를 붙이고 항상 역순으로 4 문자의 리터럴을 사용합니다 : ULONG tagMemory = 'kscf';

해석은 플랫폼에 따라 다르지만 문자 스트림입니다.