2016-03-31 14 views
1

Bir std::arrayboost::variant nesne var ve her birinde bir şey bir başvuru dönen, dizideki bir öğe ziyaret eden bir boost::static_visitor oluşturmaya çalışıyorum değişken üye türleri. Yani, işte bir lokma var benim uygulanmasını taklit bir kod parçacığı var:boost :: varyant ziyaretçi dönüş hatası (en can sıkıcı ayrıştırma?)

#include <boost/variant.hpp> 
#include <array> 

struct SomeType {}; 

struct A { 
    SomeType something; 
    SomeType& someMethod() { return something; } 
}; 

struct B { 
    SomeType something; 
    SomeType& someMethod() { return something; } 
}; 

struct C { 
    SomeType something; 
    SomeType& someMethod() { return something; } 
}; 

typedef boost::variant<A, B, C> MyVariant; 

class SomeVisitor : public boost::static_visitor<> { 
public: 
    template<typename T> 
    SomeType& operator()(T& operand) const { 
    return operand.someMethod(); 
    } 
}; 

class MyVariants { 
public: 
    SomeType* getSomething(unsigned index); 

private: 
    static const size_t count = 100; 
    std::array<MyVariant, count> variants_; 
}; 

SomeType* MyVariants::getSomething(unsigned index) { 
    if(index < count) { 
    MyVariant& variant = variants_[index]; 
    SomeType& something = boost::apply_visitor(SomeVisitor(), variant); 
    return &something; 
    } 
    else { 
    return nullptr; 
    } 
} 

Bu pasajı clang 3.6.2 ile derler, ama gcc 5.3.1 tükürür (boost varyant başlıklarından birkaç düzine hataları ardından aşağıdaki)

test.cpp:43:47: error: invalid initialization of non-const reference of type 'SomeType&' from an rvalue of type 'boost::static_visitor<>::result_type {aka void}' 
    SomeType& something = boost::apply_visitor(SomeVisitor(), variant); 

Tüm hatalar aynı şeyi söylemek gibi görünüyor - ziyaretçinin dönüş tipi void ve ben bir SomeType& o bağlamak mümkün değil. Bu benim cümle ile iyi derleme beri SomeVisitor benim uygulama ile herhangi bir sözdizimi hataları olduğunu sanmıyorum.

This question ve this question bir boost::static_visitor tarafından üretilen benzer hataları gösterir ve her iki C++ 'ın en-üzücü-ayrıştırma ile açıklanmıştır. Her iki bu soruların olarak, konu böyle bir şey (yukarıdaki benim pasajımızdaki türleri kullanarak) idi: Bu bağlamda

MyVariant variant(A()); 
SomeType& something = boost::apply_visitor(SomeVisitor(), variant); 

, ben en can sıkıcı ayrıştırma uygular anlayabiliyorum. MyVariant variant(A());, derleyici için belirsiz olabilir. Bunun, snippet'ime nasıl uygulandığını bilmiyorum, çünkü MyVariant& variant = variants_[index] oldukça açık görünüyor. Bu soruların benim sorunumla ilgili olup olmadığını bilmiyorum./Help

Herhangi bir tavsiye bir cevap olarak verilmiştir

+2

Sen static_visitor şablon argümanı listesinde dönüş türünü belirtmek gerekir. Boş bırakmak, derleyiciye konuşmacının boşa döneceğini söylüyor. –

+0

Teşekkürler! Tam olarak sorun buydu. Ben birkaç hafta önce (sağ sözdizimi ile) bir dönüş değeri ile bir "boost :: static_visitor" yaptım, bu yüzden ben her zaman –

+0

utanıyorum. C++ 14 ile daha sonraki sürümlerde statik bir ziyaretçiye ihtiyacınız olmadığını unutmayın. Auto & 'argüman türüne sahip bir lambda yeterli olacaktır. –

cevap

1

Comment mutluluk duyacağız:

Sen static_visitor şablon argümanı listesinde dönüş türünü belirtmek gerekir. Boş bırakmak, derleyiciye konuşmacının boşa döneceğini söylüyor.

class SomeVisitor : public boost::static_visitor<SomeType&> { 
public: 
    template<typename T> 
    SomeType& operator()(T& operand) const { 
    return operand.someMethod(); 
    } 
}; 

Alternatif 14 ++ c boost sonraki sürümlerinde:

auto& something = boost::apply_visitor([](auto& x) { return x.someMethod(); }, 
             variant); 
İlgili konular