2

我想用 C++ 制作一个简单的链表类和其他数据结构,以适应面向对象的编程。在编辑了我的旧 C 代码后,我得到了这样的东西(我刚刚包含了其中一个函数):

template<typename T> class llist
{
    public:
        T data;
        llist<T>* next;

        llist() {next=nullptr;}
        llist(const T& d) {data=d;next=nullptr;}
};

template<class T> llist<T>** llistAdd(llist<T> **l,const T& d)
{
    llist<T> *temp=*l;
    (*l)=new llist<T>(d);
    (**l).next=temp;
    return &(**l).next;
}

使用如下:

int main()
{
    llist<int>* my_integer_list = nullptr;

    llistAdd(&my_integer_list,42);
    llistAdd(&my_integer_list,128);
    llistAdd(&my_integer_list,1337);

    for(auto itr = &my_integer_list; (*itr) != nullptr; llistItrAdv(&itr))
        cout<<(**itr).data<<endl;

    llistClear(&my_integer_list);

    return 0;
}

这一切都完美无缺。问题是 C++ OOP 风格使用方法而不是像llistAdd(..). 问题是我的代码适用于指向指针的指针,甚至是指向指针的指针(请参阅 参考资料llistItrAdv(..))。如果我使用方法,我将需要执行以下操作:

template<typename T> llist<T>* llist<T>::Add(const T& d)
{
    llist<T> *temp = new llist<T>(d);
    temp->next = this;
    return temp;
}

int main()
{
    llist<int>* my_integer_list = nullptr;

    my_integer_list = my_integer_list->Add(42);

    my_integer_list = my_integer_list->Clear();

    return 0;
}

然而,这会产生丑陋的代码并且容易出现内存泄漏。必须有更好的方法来使用方法来做到这一点,但我真的想不出任何东西。我试图为指针创建方法,但这在 C++ 中是非法的。你们能告诉我像我这样的 OOP 风格的交易课程如何正确吗?

4

1 回答 1

3

您遇到的问题源于您的llist类实际上是链表中的单个节点,而不是整个列表,因此拥有add方法没有意义。您会注意到,在您的非 OOP 代码中实际上也是如此 - 该 llistAdd函数不是作用于llist对象,而是作用于具有对象引用的对象(这里只是一个指针)llist。这为您的问题提出了解决方案:将您的旧类重命名为llistnode并创建一个新llist类,其指针指向llistnode列表的头部,并在这个新类上实现

template<typename T> class llistnode
{
  public:
    T data;
    llistnode<T>* next;

    llistnode() {next=nullptr;}
    llistnode(const T& d) {data=d;next=nullptr;}
};

template<typename T> class llist
{
  private:
    llistnode<T>* head;

  public:
    void Add(const T& d) {
        llistnode<T>* new_node = new llistnode<T>(d);
        new_node.next = head;
        head = new_node;
    }
};
于 2013-06-20T17:57:45.353 回答