C++自定义模板LinkedList崩溃添加std :: string

Imh*_*tep 0 c++ string list nodes

出于学术目的,我正在尝试开发一些"文本冒险游戏".我必须自己实现所有数据结构.现在,我在实现通用(模板)LinkedList时遇到了一些问题.

具体来说,这个数据结构适用于所有(原始数据类型和自定义对象)但字符串!(标准库字符串).

当我尝试将字符串添加到列表时,应用程序崩溃并出现以下错误(在控制台中):

"在抛出'std :: logic_error'的实例后调用终止what():basic_string :: _ S_constructor null无效"

该列表使用头节点作为第一个最后一个节点实现为"双链表"

这里的代码("Abstract"List接口):

#ifndef LIST_H_
#define LIST_H_

template <class T>
class List
{
public:
 virtual ~List() {}
 virtual T get(int position) = 0;
 virtual List* add(T item) = 0;
 virtual List* insert(T item, int position) = 0;
 virtual List* remove(int position) = 0;
 virtual int size() const = 0;
 virtual bool isEmpty() const = 0;

protected:

private:

};

#endif /* LIST_H_ */
Run Code Online (Sandbox Code Playgroud)

这是LinkedList实现("节点"类):

#include "List.h"
#include <stdlib.h>

#ifndef LINKEDLIST_H_
#define LINKEDLIST_H_

template <class T>
class ListNode
{
public:
ListNode(T item)
{
    mItem = item;
    mNext = NULL;
    mPrev = NULL;
}

ListNode(T item, ListNode<T>* next, ListNode<T>* prev)
{
    mItem = item;
    mNext = next;
    mPrev = prev;
}


~ListNode()
{
    delete &mItem;
}


T getItem()
{
    return mItem;
}


ListNode<T>* getNext()
{
    return mNext;
}


ListNode<T>* getPrev()
{
    return mPrev;
}


void setItem(T item)
{
    mItem = item;
}


void setNext(ListNode<T>* next)
{
    mNext = next;
}


void setPrev(ListNode<T>* prev)
{
    mPrev = prev;
}

protected:
private:
T mItem;
ListNode<T> *mNext, *mPrev;
};
Run Code Online (Sandbox Code Playgroud)

LinkedList类:

template <class K>
class LinkedList : public List<K>
{
public:
LinkedList()
{
    mSize = 0;
    mFirstNode = NULL;
}

~LinkedList()
{
    // implementazione distruttore tramite ciclo sui nodi
}

K get(int position)
{
    K item = NULL;

    ListNode<K>* targetNode = getNodeAtPosition(position);
    if (targetNode != NULL) item = targetNode->getItem();

    return item;
}

List<K>* add(K item)
{
    if (mFirstNode == NULL)
    {
        mFirstNode = new ListNode<K>(item);
        mFirstNode->setNext(mFirstNode);
        mFirstNode->setPrev(mFirstNode);
    }
    else
    {
        ListNode<K>* newNode = new ListNode<K>(item, mFirstNode, mFirstNode->getPrev());
        mFirstNode->getPrev()->setNext(newNode);
        mFirstNode->setPrev(newNode);
    }

    mSize++;
    return this;
}

List<K>* insert(K item, int position)
{
    ListNode<K>* targetNode = getNodeAtPosition(position);

    if (targetNode != NULL)
    {
        ListNode<K>* newNode = new ListNode<K>(targetNode->getItem(), targetNode->getNext(), targetNode);
        targetNode->setItem(item);
        targetNode->setNext(newNode);

        mSize++;
    }

    return this;
}

List<K>* remove(int position)
{
    ListNode<K>* targetNode = getNodeAtPosition(position);
    if (targetNode != NULL)
    {
        targetNode->setItem(targetNode->getNext()->getItem());
        targetNode->setNext(targetNode->getNext()->getNext());

        //delete targetNode->getNext();
        mSize--;
    }

    return this;
}

int size() const
{
    return mSize;
}

bool isEmpty() const
{
    return (mFirstNode == NULL) ? true : false;
}

protected:
ListNode<K>* getNodeAtPosition(int position)
{
    ListNode<K>* current = NULL;

    if (mFirstNode != NULL && position < mSize)
    {
        current = mFirstNode;

        for (int i = 0; i < position; i++)
        {
            current = current->getNext();
        }
    }

    return current;
}

private:
     int mSize;
     ListNode<K>* mFirstNode;
};

 #endif /* LINKEDLIST_H_ */
Run Code Online (Sandbox Code Playgroud)

建议?

Zac*_*and 5

你的部分问题在这里:

ListNode(T item)
{
    mItem = item; // for a std::string, this will be a class member, non-pointer
    mNext = NULL;
    mPrev = NULL;
}

ListNode(T item, ListNode<T>* next, ListNode<T>* prev)
{
    mItem = item; // same here
    mNext = next;
    mPrev = prev;
}


~ListNode()
{
    delete &mItem; // you are attempting to delete an item you never created
}
Run Code Online (Sandbox Code Playgroud)

您应该更改构造函数以T*在堆上创建对象(然后将在析构函数中删除),或者delete从析构函数中删除该行.

std::string顺便提一下,这个问题不仅仅是显而易见的.