2010-12-07 45 views
0

多重继承我有以下情况:C++从相同的基本模板歧义

我有一个使用在想要被放在一个列表类继承了ListNode类的List类。

struct _List_node_base 
{ 
... 
void _M_hook(_List_node_base* const __position); 
void unhook(); 
}; 


template<typename _Tp> 
class ListNode : public _List_node_base 
{ 
... 
     typedef _Tp* pointer; 
public: 
pointer GetNext(); 
pointer GetPrev(); 
}; 


template<typename _Tp> 
class List 
{ 
    ... 
}; 

我也有一个HashTable类,类似于列表有一个HashNode类。 HashNode使用ListNode以便放入适当散列槽中的列表中。

template<typename _KeyType, typename _ObjectType> 
    class HashNode : public ListNode<ObjectType> 
    { 
... 
    public: 
      _KeyType GetHashKey() 
    }; 



    template<typename _KeyType, typename _ObjectType, typename _HashFunctionType> 
    class HashTable 
    { 
     //example 

    template<typename _KeyType, typename _ObjectType, typename _HashFunctionType> 
    void HashTable<_KeyType, _ObjectType, _HashFunctionType>::Insert(_ObjectType *object) 
    { 
     uint pos = hashFunction(object->GetHashKey(), tableSize); 

     hashTable[pos].PushBack(object); 
    } 

    }; 

我有一个类,既想列表和可哈希。

class A : public HashNode<SomeKeyType_t, A>, public ListNode<A> 
{ 
... 
}; 

的问题是,编译抱怨,在List_node_base成员具有A级

无论在哈希类和List类的暧昧的基础上,他们使用直接ListNode和List_node_base方法在类A上。

基本上,我想让类A可哈希和列表,但是HashNode的ListNode功能不应暴露在类HashTable的实现之外。

此外,类的要点是它们必须是非侵入性的,动态分配和复制类是不允许的。否则,这将通过创建一个容器类来解决。

+2

按照你的设计,HashNode 已经是ListNode 所以不是“A类:HashNode ”够了吗? – MerickOWA 2010-12-07 20:48:30

+1

设计好的容器库非常困难。发明轮子的理由是什么?比如说,Boost.Intrusive已经有了非常成熟的侵入式容器实现。 – Stas 2010-12-07 20:59:38

+0

**不要**用下划线开始您的标识符:[使用下划线是什么](http://stackoverflow.com/questions/228783/what-are-the -rules-约-使用-AN-下划线在-AC-标识符/ 228797#228797)。这个`_List_node_base`(几乎每个类型或模板参数都是保留的,甚至有几个参数)被保留供系统使用。 – 2010-12-07 21:21:55

回答

1

我认为一个更好的设计是为了避免继承和使用这样的事情,而不是:

template <typename _KeyType, typename _ObjectType> 
struct HashEntry { 
    typedef ListNode<HashEntry> Node; 

    _KeyType key; 
    _ObjectType object; 
    ... 
}; 

BTW,_<uppercase-letter>...保留用于执行。你不应该在你自己的符号名称中使用它。

0

由于HashNode是ListNode的派生类,因此您在对象层次中有两次相同的“父”类。

避免尽可能多地继承非抽象类。如果您绝对需要从2个基类继承的类,则应该重新评估您的设计模式和/或查看您的类可以实现的接口(抽象)类。

3

我不确定我是否喜欢这种设计,但无论如何,您都可以在_List_node_base上使用virtual inheritance来解决您的问题。

0

你可能使用STL/boost容器来保存智能指针(例如boost :: shared_ptr)来解决你的类必须是非复制可构造和非可复制赋值的问题吗?