2013-05-18 42 views
2

從我這裏的其他問題Copying from std container frm arbitrary source object我設法讓模板幾乎在MSVC下工作。不幸的是,編譯器崩潰,添加了一個構造函數來接受所有類型的std容器,而我的真實項目仍然在gcc中。現在,當我在gcc中使用此模板時,出現了幾個我不知道如何解決的錯誤。模板類構造函數不工作

template <class T> class ReadOnlyIterator 
{ 
public: 
    template <typename V, typename U> 
    struct is_same 
    { 
     enum { value = 0 }; 
    }; 

    template <typename V> 
    struct is_same<V, V> 
    { 
     enum { value = 1 }; 
    }; 

    template <bool, typename> 
    struct enable_if 
    {}; 

    template <typename V> 
    struct enable_if<true, V> 
    { 
     typedef V type; 
    }; 

template <typename Container> 
    typename enable_if< 
    is_same<T, typename Container::value_type>::value, ReadOnlyIterator<T>&>::type operator= (const Container &v) 
    { 
     return *this; 
    } 

    template <typename Container> 
    ReadOnlyIterator(const Container &v, typename enable_if<is_same<T, typename Container::value_type>::value, void>::type * = 0) 
    { 
     mVector = v; 
     mBegin = mVector.begin(); 
    } 
}; 

我的目標是讓分配是這樣的:

std::vector<SimpleClass *>v; 
std::list<SimpleClass *>l; 
ReadOnlyIterator<SimpleClass *> t0 = v; 
ReadOnlyIterator<SimpleClass *> &t1 = v; 
ReadOnlyIterator<SimpleClass *> t2 = ReadOnlyIterator<SimpleClass *>(v); 
ReadOnlyIterator<SimpleClass *> t3 = l; 

t0 = v; 
t0 = l; 

我更新了上面的代碼並恢復我申請了錯誤的變化。所以,現在我只能拿到原來的問題,我試圖修復:

ReadOnlyIterator<SimpleClass *> &t1 = v; 

導致:

invalid initialization of reference of type 'ReadOnlyIterator<SimpleClass*>&' from expression of type 'std::vector<SimpleClass*, std::allocator<SimpleClass*> >' 
+1

請注意,在你之前的問題中,我使用'struct'而不是'class'作爲助手('struct'默認情況下具有公共訪問權限,'class'具有私有權限),並且我將它們命名爲namespace-scope,而不是嵌套在'ReadOnlyIterator'中。 – Angew

+0

好的。我改回了它,但它仍然不起作用,因爲我得到了與上面相同的錯誤。 – Devolus

+0

請參閱leemes的答案。您至少可以正確複製以前的答案。 – Angew

回答

1

正如你已經發現,如果在其他模板類中寫一個模板類,你必須給模板參數不同的名稱:

template <typename U, typename V> 
struct is_same<U, V> 
{ 
    enum { value = 0 }; 
}; 

is_same專業化,你必須使用同一類型指定專業類名稱時,(你也可以將其命名爲U,但使用相同的名稱所有三個地方:在專業類名稱在模板參數列表以及):

template <typename V> 
struct is_same<V, V> 
{ 
    enum { value = 1 }; 
}; 

另外,正如評論中提到的,你應該使這些幫助類struct而不是class;那麼你不必寫public:

1

我承擔錯誤來自第二個聲明,這簡直就是非法的。您正在創建對非const的引用ReadOnlyIterator,因此您無法使用臨時文件(例如由轉換構造函數創建的文件)初始化該文件。如果您需要參考,請使用對const的引用。但你可能不需要一個。

第三聲明:

ReadOnlyIterator<SimpleClass *> t2(v) = v; 

在語法上是錯誤的。

+0

感謝您指出,它應該是'\t ReadOnlyIterator t2 = ReadOnlyIterator (v);'和我在問題中解決了它。 – Devolus