2017-08-29 79 views
3

我試圖初始化模板類中的數組,並將this指針傳遞給數組中的所有元素。 這是我的課是什麼樣子:使用'this'指針初始化std :: array

template<int NUM> class outer_class; 

template<int N> 
class inner_class { 
    private: 
    outer_class<N> *cl; 
    public: 
    inner_class(outer_class<N> *num) { 
    cl = num; 
    } 
    void print_num() { 
    cl->print_num(); 
    } 

}; 

template<int NUM> class outer_class { 
private: 
    int number = NUM; 

    // --> here I basically want NUM times 'this' <-- 
    std::array<inner_class<NUM>, NUM> cl = { this, this, this, this }; 

public: 

    void print_num() { 
    std::cout << number << std::endl; 
    } 

    void print() { 
    cl[NUM - 1].print_num(); 
    } 
}; 

int main() { 
    outer_class<4> t; 
    t.print(); 

    return 0; 
} 

我怎樣才能通過this指針存儲的outer_class陣列中的所有inner_class元素(在C++ 11)?

回答

9

首先,在構造函數或任何其他成員函數之外不能有這樣的this。在這裏你必須在初始化列表中初始化cl

std::*_sequence東西一起使用delegating constructor

template<int NUM> class outer_class { 
    ... 

    template <std::size_t... Integers> 
    outer_class(std::index_sequence<Integers...>) 
    : cl{(static_cast<void>(Integers), this)...} 
    {} 

public: 
    outer_class(/* whatever */) : outer_class(std::make_index_sequence<NUM>{}) {} 
}; 

旁註:

  • print成員函數應標明const,因爲它們不修改您的會員。您可能需要使用std::array::back()
+1

如果序列構造函數是私有的,會不會更好? – Rakete1111

+0

@ Rakete1111對,編輯。 –

+0

@奧尼爾Thx爲您的答案,很好,很容易 –

4

你可以使用一些輔助功能,然後使用這些功能,如初始化成員:

template <std::size_t I, class T> 
T copy(T t) { return t; } 

template <class T, std::size_t... Is> 
constexpr std::array<T, sizeof...(Is)> copy_n(T const& t, std::index_sequence<Is...>) { 
    return {copy<Is>(t)... }; 
} 

template <class T, std::size_t N> 
constexpr std::array<T, N> copy_n(T const& t) { 
    return copy_n(t, std::make_index_sequence<N>{}); 
} 
在類

然後:

std::array<inner_class<NUM>, NUM> cl; 

outer_class() : cl(copy_n<inner_class<NUM>, NUM>(this)) { } 

注:

  • [待驗證]您不能在默認會員中使用this初始化器,所以你需要有一個自定義的構造函數;
  • 你需要明確指定inner_class<NUM>copy_n第一個模板參數,因爲otherwize T會推導出outer_class<NUM>*,雖然有來自outer_class<NUM>*inner_class<NUM>的隱式轉換,從沒有std::array<outer_class<NUM*>, NUM>std::array<inner_class<NUM>, NUM>轉換;
  • 如果您使用C++ 11而非14或clang,則可能會在returncopy_n上發出警告,您可以通過添加一對額外的括號{}來消除它。
+0

@Someprogrammerdude謝謝,我真的很想知道,但沒有找到自己的信息...將更新答案。 – Holt

+1

或者它可以嗎? [似乎工作正常](http://coliru.stacked-crooked.com/a/9c9adcb807cfa68a)。 –

+0

這看起來不錯,但是有一個std :: make_index_sequence的C++ 11兼容版本嗎? –