7

我为它的值类型定义了一个带有模板的 Node 类

template<class T>
class Node {
  T val;
  public:
    Node (T & v) : val (v) {}
    ...
    void print() { cout << v << endl; }
}

大多数时候,感兴趣的节点值将是一个对象类,例如class Foo。那样的话,使用Node<Foo *>起来会更方便。但也可能是该节点将保持原始时间,例如int。然后使用Node<int>就足够了。

问题是,某些函数可能需要根据是否T为指针类型来表现不同。例如,print应该cout << *v何时是,cout << v否则。

我尝试的是定义两者:

template<class T>
class Node {
  T val;
  public:
    Node (T & v) : val (v) {}
    ...
    void print() { cout << v << endl; }
}

template<class T>
class Node<T*> {
  T* val;
  public:
    Node (T* v) : val (v) {}
    ...
    void print() { cout << *v << endl; }
}

它现在可以根据是否是来选择合适的定义,Node<int> or Node<int *>但是问题就变成了,这两个定义会共享很多代码。我想知道是否有更好的方法来实现这一点。

4

2 回答 2

4

请参阅:C++ 模板专业化,在可能是指针或引用的类型上毫无歧义地调用方法

相同的技术应该在这里工作,允许您在两种情况下统一处理val作为引用(或指针)。

CRTP可以帮助减少代码重复,同时允许两个专业的通用代码没有任何开销。

请注意,当您有时使用指针,有时使用实例时,所有权语义会变得很棘手——val如果有时它是参数的指针,有时它是参数的副本,那么它的生命周期是什么,以及如何强制执行它?

于 2013-01-25T19:27:44.260 回答
0

好吧,还有另一种方法可以做到这一点。您应该使用类型特征,它们在编译时进行评估。这是您可以修改的方式。

template<class T>
class Node {
  T val;
  public:
    Node (T & v) : val (v) {}
    ...
    void print() { 
      if(std::is_pointer<T>::value)
        cout << *v << endl;
      else
        cout << v << endl;
    }
}
于 2019-09-17T08:31:10.050 回答