0

私は次のコードを持っています:

template<class T>
class RandomTreeNode {

public:
    typedef typename RandomTreeFunction<T>::function_ptr function_ptr;
    RandomTreeNode(): left(NULL), right(NULL), threshold(0.0), is_a_leaf(false), data(NULL), function(0){
    }
    void set_function(function_ptr function){this->function = function;}
    function_ptr get_function(){ return this->function;}

    void set_threshold(double threshold){this->threshold = threshold;}
    double get_threshold(){return threshold;}

    void create_left_child(){this->left = RandomTreeNode<T>();}
    //returning references so that they can be altered in a recursive tree build algo without excessive copying
    RandomTreeNode<T>& get_left_child(){return left;}

    void create_right_child(){this->right = RandomTreeNode<T>();}
    RandomTreeNode<T>& get_right_child(){return this->right;}

    bool is_leaf(){return this->is_a_leaf;}
    void mark_as_leaf(){this->is_a_leaf = true;}

    const std::vector<T> get_data(){
        return data;
    }
    void set_data(std::vector<T>& data){
        this->data = data; 
    }

private:
    RandomTreeNode<T> left;
    RandomTreeNode<T> right;
    double threshold;
    function_ptr function;
    std::vector<T> data;
    bool is_a_leaf;

};

コンパイルすると、次のようになりますerror: 'RandomTreeNode<T>::left' has incomplete type。なぜ何かアイデアはありますか?

4

4 に答える 4

3

それはあなたが現在定義しているタイプだからです。タイプが同じタイプのメンバーを持つことは意味がありません(初心者の場合、サイズは無限になります)。あなたが望むのは、直接のインスタンスではなく、のポインタを持つことだと思います。RandomTreeNode<T>

于 2012-10-22T16:33:27.613 に答える
1

このクラス内でクラスのインスタンスを宣言することはできません。

ここであなたは宣言しRandomTreeNode<T> left;RandomTreeNode<T> right;あなたの宣言の中でRandomTreeNode。したがって、型の宣言は完全ではありません。

RandomTreeNode<T>このエラーを回避するには、ポインタを使用する必要があります。

于 2012-10-22T16:36:08.627 に答える
0

正しくコンパイルされているコード(http://codepad.org/ltpxM60i)

以下のコードが正しくコンパイルされるようになりました

**template<class T>
class RandomTreeFunction{
      class function_ptr{
       };
};**
template<class T>
class RandomTreeNode {

public:
    typedef  typename RandomTreeFunction<T>::function_ptr function_ptr;
    RandomTreeNode(): left(NULL), right(NULL), threshold(0.0), is_a_leaf(false), data(NULL), function(0){
    }
    void set_function(function_ptr function){this->function = function;}
    function_ptr get_function(){ return this->function;}

    void set_threshold(double threshold){this->threshold = threshold;}
    double get_threshold(){return threshold;}

    void create_left_child(){this->left = RandomTreeNode<T>();}
    //returning references so that they can be altered in a recursive tree build algo without excessive copying
    RandomTreeNode<T>& get_left_child(){return left;}

    void create_right_child(){this->right = RandomTreeNode<T>();}
    RandomTreeNode<T>& get_right_child(){return this->right;}

    bool is_leaf(){return this->is_a_leaf;}
    void mark_as_leaf(){this->is_a_leaf = true;}

    const std::vector<T> get_data(){
        return data;
    }
    void set_data(std::vector<T>& data){
        this->data = data; 
    }

private:
    RandomTreeNode<T> left;
    RandomTreeNode<T> right;
    double threshold;
    function_ptr function;
    std::vector<T> data;
    bool is_a_leaf;

};
int main(){
return 0;
}

function_ptrが定義されていないと思います

typedef typename RandomTreeFunction<T>::**function_ptr** function_ptr;

タイプ名の場合、ここで適用されるルールは次のとおりです(参照:-http : //pages.cs.wisc.edu/~driscoll/typename.html

ルール

typename is prohibited in each of the following scenarios:
        Outside of a template definition. (Be aware: an explicit template specialization (more commonly called a total specialization, to contrast with partial specializations) is not itself a template, because there are no missing template parameters! Thus typename is always prohibited in a total specialization.)
        Before an unqualified type, like int or my_thingy_t.
        When naming a base class. For example, template <class C> class my_class : C::some_base_type { ... }; may not have a typename before C::some_base_type.
        In a constructor initialization list.
    typename is mandatory before a qualified, dependent name which refers to a type (unless that name is naming a base class, or in an initialization list).
    typename is optional in other scenarios. (In other words, it is optional before a qualified but non-dependent name used within a template, except again when naming a base class or in an initialization list.)

したがって、function_ptrの型を定義する必要があるかもしれません。

于 2012-10-22T17:21:16.733 に答える
-1

前方宣言を試してください。これは、プログラムの開始時にグローバルスコープで記述してください。

template<class T>
class RandomTreeNode ;

宣言しようとしている型の変数を宣言しているため、エラーが発生します。

于 2012-10-22T16:34:15.187 に答える