C 함수 구문, 매개 변수 목록 뒤에 선언 된 매개 변수 유형


79

저는 비교적 C를 처음 접했습니다. 전에 본 적이없는 함수 구문의 한 형태를 보았습니다. 여기서 매개 변수 유형은 해당 매개 변수 목록 뒤에 정의됩니다. 누군가가 일반적인 C 함수 구문과 어떻게 다른지 설명해 줄 수 있습니까?

예:

답변:


65

이것이 여전히 지원되는 매개 변수 목록의 이전 스타일 구문입니다. K & R C에서는 유형 선언을 생략 할 수도 있으며 기본값은 int입니다. 즉

동일한 기능이 될 것입니다.


17
C89 / 90과 C99 모두 공식적으로 K & R 스타일 선언을 지원합니다. 그러나 C99에서는 모든 매개 변수를 명시 적으로 선언해야합니다 (더 이상 "암시 적 int"규칙 없음).
AnT 2010 년

1
나는 파티에 늦는 것이 싫지만 (4 년 후처럼?), C99 에서는 매개 변수 목록 이나 함수에서 명시 적으로 선언해야한다고 말하는 건가요? 예를 들어, 기본 int 규칙-더 이상 int로 기본 설정되지 않으므로 매개 변수 목록에 유형이 제공되지 않은 경우 사용하기 전에 해당 유형을 함수에서 선언해야 합니까?
Chris Cirefice 2013 년

1
@ChrisCirefice 4 년 후 답변 : C99에서는 모든 매개 변수가 매개 변수 목록에 선언되어야합니다. 함수에 선언 된 변수는 기본값으로 설정되지 않았 int으므로 명시 적으로 선언해야합니다.
Frank Kusters

28

또한 흥미로운 점은 프로토 타입이없는 함수와 함수의 호출 규칙 차이입니다. 이전 스타일 정의를 고려하십시오.

이 경우 호출 규칙은 모든 인수가 함수에 전달되기 전에 승격된다는 것입니다 (예 : float인수는 double전달되기 전에 먼저로 승격됩니다 ). 따라서 fa를 수신 double했지만 매개 변수에 유형 float(완벽하게 유효한)이있는 경우 컴파일러는 함수의 본문을 실행하기 전에 double을 float로 변환하는 코드를 내 보내야합니다.

프로토 타입을 포함하면 컴파일러는 더 이상 자동 승격을 수행하지 않으며 전달 된 모든 데이터는 마치 할당에 의해 프로토 타입의 매개 변수 유형으로 변환됩니다. 따라서 다음은 합법적이지 않으며 정의되지 않은 동작이 발생합니다.

이 경우 함수의 정의는 정의가 구식이기 때문에 제출 된 매개 변수를 double(승격 된 양식) 에서로 변환합니다 float. 그러나 함수에 프로토 타입이 있기 때문에 매개 변수는 부동 소수점으로 제출되었습니다. 예를 들어, clang은

main.c : 3 : 9 : 경고 : K & R 함수 매개 변수의 승격 된 유형 'double'이 이전 프로토 타입에서 선언 된 매개 변수 유형 'float'와 호환되지 않습니다. [-Wknr-promoted-parameter]

모순을 해결하는 옵션은 다음 두 가지입니다.

선택권이 있다면 옵션 2를 선호해야합니다. 이전 스타일 정의를 제거하기 때문입니다. 함수에 대해 이와 같이 모순되는 함수 유형이 동일한 번역 단위에 나타나면 컴파일러는 일반적으로 알려줍니다 (필수는 아님). 이러한 모순이 여러 번역 단위에 나타나는 경우 오류가 눈에 띄지 않게되어 버그를 예측하기 어려울 수 있습니다. 이러한 오래된 스타일 정의를 피하는 것이 가장 좋습니다.


10

이것이 바로 호출자 K & R 스타일 또는 구식 선언입니다.

이 선언은 현대 선언과 크게 다릅니다. K & R 선언은 함수 의 프로토 타입 을 도입하지 않습니다 . 즉, 매개 변수 유형을 외부 코드에 노출하지 않습니다.


4

차이가 없습니다. 단지 그것이 C에서 함수 선언을위한 오래된 구문이라는 것입니다. ANSI 이전에 사용되었습니다. 80 년대의 친구들에게 줄 계획이 아니라면 그런 코드를 작성하지 마십시오 . 또한 암시 적 유형 가정에 의존하지 마십시오 (다른 답변이 제안하는 것처럼)


잘 C99 이전; 1989 년에 표준화 된 ANSI 이전 버전이 사용되었지만 1983 년에 프로세스가 시작되었습니다.
Brian Campbell

2
Ahem ... K & R 스타일 선언은 C99에 의해 공식적으로 지원됩니다. 단 하나의 사소한 변경 만 있습니다. 더 이상 "암시 적 int"가 없으며 모든 매개 변수를 명시 적으로 선언해야합니다.
AnT 2010 년

비판 속에서 나는 당신에게 동의한다고 말해야합니다 :하지 마십시오.
BobbyShaftoe 2010 년

4

함수 정의에 대한 이전 구문은 여전히 ​​작동하지만 (컴파일러에게 요청하면 경고와 함께) 함수 프로토 타입을 제공하지 않습니다.
함수 프로토 타입이 없으면 컴파일러는 함수가 올바르게 호출되었는지 확인하지 않습니다.

프로그램이 실행되면 내 컴퓨터의 출력은 다음과 같습니다.


1

똑같지 만 오래된 패션. 아마도 그것이 오래된 레거시 코드임을 발견했을 것입니다.


0

늙었 든 아니든, 나는 낡은 것이 무엇이고 어떤 것이 .. 피라미드와 같은 고대인지 논쟁 할 것입니다. 그러나 오늘날의 과학자 중 어느 누구도 그것이 어떻게 만들어 졌는지 단서가 없습니다. 되돌아 보면, 오래된 프로그램은 오늘날에도 메모리 누수없이 작동하지만 이러한 "새로운"프로그램은 더 자주 실패하는 경향이 있습니다. 여기에 트렌드가 보입니다.

아마도 그들은 함수를 실행 가능한 본문을 가진 구조체로 보았다. 수수께끼를 풀기 위해서는 ASM에 대한 지식이 필요합니다.

편집, 인수 이름을 전혀 제공 할 필요가 없음을 나타내는 매크로를 찾았습니다.

다음은 사용 예입니다. library는 zlib-1.2.11 입니다.

그래서 두 번째 추측은 함수 오버로딩에 대한 것입니다. 그렇지 않으면 이러한 인수가 사용되지 않았습니다. 하나의 구체적인 기능, 이제 동일한 이름을 가진 무한한 양의 기능.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.