2011-08-24 2 views
3

다음은 코드입니다.C++ 0x에서 람다 내부에 구조체 변수를 선언 할 수없는 이유는 무엇입니까?

#include<struct.h> 
#include<iostream> 
#include<functional> 
using namespace std; 

void LambdaTest(const function <struct dummy (void)>& f) 
    { 
    struct dummy test = f(); 
    cout<<test.a<<endl; 
    } 

int main() 
    { 
    int val = 5; 
    struct dummy dum; 

    auto func = [val](void) -> struct dummy 
         { 
         dummy temp; 
         temp.a = val; 
         return temp; 
         }; 

    LambdaTest(func); 
    return 0; 
    } 

struct.h 파일은 매우 간단합니다.

struct dummy 
    { 
    int a; 
    }; 

GCC는

lambda_struct.cpp:19:38: error: field ‘temp’ has incomplete type

이 허용되는 불평? 그렇다면 어떻게 수정해야합니까? 그렇지 않다면, 그 이유는 무엇입니까?

편집 :

(다른 사람에 의해 발견 된) 코드의 반환 형식 버그는 이제 수정되었습니다.

해결책 :

문제는 C + +0 표준 람다 정의 자체의 반환 형식에 새로운 구조체 (너무 아마도 클래스)에 정의를 수 있다는 것입니다. 따라서 반환 키워드에 struct 키워드가 있으면 컴파일러는 이것이 새로운 유형이라고 생각하여 불평하기 시작합니다.

당신이 멀리 struct 부분을 가지고 그냥 일반적으로 변수를 정의하면 고정 된 코드는 어떻게됩니까

#include<struct.h> 
#include<iostream> 
#include<functional> 
using namespace std; 

void LambdaTest(const function <struct dummy (void)>& f) 
    { 
    struct dummy test = f(); 
    cout<<test.a<<endl; 
    } 

int main() 
    { 
    int val = 5; 
    struct dummy dum; 

    auto func = [val](void) -> dummy 
         { 
         dummy temp; 
         temp.a = val; 
         return temp; 
         }; 

    LambdaTest(func); 
    return 0; 
    } 
+0

내가지고있어 오류 : 다음 컴파일 및 실행은

#include<iostream> #include<functional> using namespace std; struct dummy { int a; }; void LambdaTest(const function <dummy (void)>& f) { dummy test = f(); cout<<test.a<<endl; } int main() { int val = 5; dummy dum; auto func = [val](void) -> dummy { dummy temp; temp.a = val; return temp; // return the temp struct }; LambdaTest(func); return 0; } 

출력을 예상대로. '익명 네임 스페이스 ':: :: operator()': 값을 반환해야합니다. 일단 내가 컴파일하고 출력 5 고정했습니다. – 0x5f3759df

답변

7

문제는 GCC가 후행 반환에서 새 구조체 유형을 선언하고 있다고 잘못 생각하고 있으며 GCC가 선언하고 있다고 생각하는 유형과 동일한 유형의 불완전한 형식의 필드를 선언합니다.

는 또한 불평 할당과 라인에

error: 'temp' does not name a type

그것이 구성원 선언이 아닌 문을 기대하고 있기 때문이다.

에 변경 :

auto func = [val](void) -> dummy 
         { 
          struct dummy temp; 
          temp.a = val; 
          return temp; 
         }; 

가 작동합니다.

또한 함수에서 값을 반환하지 않으면 정의되지 않은 동작이 발생할 수 있습니다.

+0

이 대답은 나의 의구심을 고쳤습니다. 고마워. – rpg

+0

이 대답은 잘못되었습니다. 후행 반환 형식에서 구조체를 정의 할 수 없습니다. 이것은 g ++ 버그 일뿐입니다. –

0

입니까? 당신은, 알고

dummy temp; 

또한, 람다 반환 값에 다른 불필요한 struct 치우는보십시오. 말하자면, 실제로 컴파일하려면 을 반환해야합니다.temp.

+0

GCC는 여전히 그것을 좋아하지 않아. – rpg

+1

놀랍게도, GCC (ideone)는 람다에서 누락 된 반환 진술에 대한 경고조차 내지 않았다. 그것은 행복하게'LambdaTest()'내에서 쓰레기를 출력합니다. – Praetorian

0

C와 달리 구조체는 별도의 네임 스페이스에 배치되지 않으므로 모든 선언에서 키워드 struct을 사용할 필요가 없습니다. 또한 코드에 오류가 있습니다. 람다는 dummy 유형의 인스턴스를 반환해야합니다.++ 당신의 람다 MSVC에 값을 반환하지 않습니다

5

관련 문제