문제

이점을 고려하여 문의하시기 바랍 코드:

template<typename T>
char (&f(T[1]))[1];

template<typename T>
char (&f(...))[2];

int main() { char c[sizeof(f<void()>(0)) == 2]; }

이메일 주소와 비밀번호 하 SFINAE 및 선택 두 번째로 과부하므로,대체 TT[1]

 void [1]()

는 잘못된 형식의 코스입니다.의 조정 매개변수 유형(배열->포인터)은 대체한 후 템플릿을 매개로 기능 매개 변수 및 확인에 대한 유효한 결과 유형을 다음과 같 14.8.2[temp.공제]설명합니다.

하지만 모두 꼬모하고 GCC 컴파일할 수 없습니다.모두 다양 진단을 수행합니다.

객 말한다:

"ComeauTest.c",line2:오류:배열의 기능은 허용되지 않습 char (&f(T[1]))[1];

GCC 말한다(버전 4.3.3):

오류:ISO C++금지하 제로 크기 배열 c

미,GCC 하지 않는 실패를 대체하지만,그것은 선택의 첫 번째 오버로드 f, 를 반환 sizeof 1,실패하는 대신하는 대신 그것은 앞까지 같은 꼬모.

무엇을 컴파일러 오른쪽 내 코드는 유효한가?를 참조하십시오거나 견적을 적절한 표준 단면도에서 당신의 대답이다.감사합니다!


업데이트:표준 자체가 포함되어 이러한 예를 목록에서 14.8.2/2.나도 몰라 왜 그것을 간과 첫:

template <class T> int f(T[5]);
int I = f<int>(0);
int j = f<void>(0); // invalid array

면 예를 들어 정보만을 보여줍의 의도를 모든 사람들이 절을 보여 위의 코드 작동해야하고 거부하는 첫 번째 과부하 있습니다.

도움이 되었습니까?

해결책

작은 주이지만,매우 드문,내가 찾은 어떤 경우는 곳에 나가 믿는 꼬모 컴파일러는 그것이 잘못이지만,이러한 경우에는 그래서는 그는 항상 더블 트리플 검사 당신의 가정을!

내가 있는 이유에 대한의 행동은 g++.나는 확실하지 않 그 지정된 정확하게 때 매개변수 유형은 조정:

다음 사항을 고려하십시오:

template<typename T>
struct A
{
  void bar (T[10]);
};

template<typename T>
void A<T>::bar (T*)
{
}

의 정의는'바'은 법적으로"T[10]"붕괴를"T*".나 아무것도 표시되지 않은 표준을 금지하는 컴파일러에서 을 수행하의 조정을 8.3.5 에 대하여 템플릿을 선언 고 그것도 성능을 향상에 올 때 하중 초과 일치합니다.

이 적용의 예,g++수 있습 치료로 그것:

template<typename T>
char (&f( T* ))[1];

template<typename T>
char (&f(...))[2];

int main() { char c[sizeof(f<void()>(0)) == 2]; }

위,대체 매개변수의 법적 포인터 기능보다는 배열의 기능이 있다.

그래서 나는 뭔가가있는 경우 prohibts 조정 기능에 대한 매개변수(8.3.5)두 번?

개인적으로,나는 생각을 허용하는 조정생 두 번 이후는 그렇지 않으면 복잡하게 일치하는 기능의 템플릿 오버로드

결론적으로,나는 그것에 대해 유효 g++선택하려면 첫 번째 과부하 기반 방법에 treates 부패 배열을 매개변수,그리고 객 잘못된 것입 지 않습을 공제 실패에 대한 배열의 기능이 있다.

물론 이제는 것을 의미(면 꼬모가 수정되었)다음 각 컴파일러 선택하는 것 다른 과부하고 여전히 수준 을 준수!:(

편집:

다만 나의 점을 설명하기 위하여,다음과 같은 코드를 살펴봅니다:

template <typename T> void foo ( T * );
template <typename T> void foo ( T * const );
template <typename T> void foo ( T [] );
template <typename T> void foo ( T [10] );
template <typename T> void foo ( T [100] );

void bar () 
{
  foo < void() > ( 0 );
}

여기에,foo 선언되었다고 다시 선언한다.는 선언하고 그래서는 매개변수 유형,한 컴파일러를 적용 규칙에 나열된 14.8.2?

내 포인트는 표준에 대해 아무것도 말하지 않는다.또한 것으로까지 나아가 말하는 표현이 떠나야하는 것 그것은 하나로 정의되지 않은""또는"정의된 구현"behaviour.

다른 팁

놀랍게도 - 이것은 VS2008에서 작동합니다. 나는 그것이 올바른 행동이거나 그렇지 않다는 증거라고 생각하지 않습니다 ...

Visual Studio는 해석 중입니다

char (&f(T[1]))[1];

t의 크기 1 배열을 가져오고 크기 1의 숯 배열에 대한 참조를 반환하는 함수로서.

표준을 읽는 것으로 이해할 때 템플릿 인수 공제 과정을 설명하려고 노력할 것입니다.

  1. 명시 적 템플릿 인수는 14.8.2/2에 설명 된대로 확인됩니다.
  2. 결과 함수 시그니처는 8.3.5에 따라 조정됩니다 (즉, 포인터 붕괴로의 배열이 수행됨).
  3. 암시 적 템플릿 인수는 14.8.2.1에 따라 추론됩니다 (이것은 2 단계에서 부분적으로 대체 된 서명에서 수행됩니다).

첫 번째 오버로드에 대한 공제는 1 단계에서 실패하므로 과부하 해상도는 두 번째 오버로드를 반환합니다. 나는 프로그램이 잘못되었다고 생각하지 않습니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top