C++;删除双链表中的元素函数 我对C++是相当新的,它是数据结构。我已经为我的双链表类创建了一些函数,但是我在删除函数方面遇到了问题。我制作了一个deleteHead()函数,它删除列表中的第一个节点,一个deleteTail()函数删除列表中的最后一个节点,最后一个deleteElement(Item)函数遍历列表并删除其中包含该项的节点
问题是,每当我试图从列表中删除唯一剩余的节点时,程序就会崩溃。i、 e如果我插入一个节点,然后在同一个节点上调用deleteElement函数(如果我插入的节点是列表中唯一的节点),程序就会崩溃 这是我的密码C++;删除双链表中的元素函数 我对C++是相当新的,它是数据结构。我已经为我的双链表类创建了一些函数,但是我在删除函数方面遇到了问题。我制作了一个deleteHead()函数,它删除列表中的第一个节点,一个deleteTail()函数删除列表中的最后一个节点,最后一个deleteElement(Item)函数遍历列表并删除其中包含该项的节点,c++,doubly-linked-list,C++,Doubly Linked List,问题是,每当我试图从列表中删除唯一剩余的节点时,程序就会崩溃。i、 e如果我插入一个节点,然后在同一个节点上调用deleteElement函数(如果我插入的节点是列表中唯一的节点),程序就会崩溃 这是我的密码 template <class T> void LinkedList<T>::deleteElement(T item) { ListItem<T>* current = head; ListItem<T>* temp;
template <class T>
void LinkedList<T>::deleteElement(T item)
{
ListItem<T>* current = head;
ListItem<T>* temp;
if (head == NULL) { // if list is empty end the function
return;
}
while (current) {
if (current->value == item) {
if (current == head) { // if item is in the head
deleteHead();
}
else if (current == getTail()) { // if item is in the tail
deleteTail();
}
// if item is between two nodes
else if (current != head && current != getTail()) {
temp = current;
temp->prev->next = temp->next;
temp->next->prev = temp->prev;
current->next = NULL;
current->prev = NULL;
if (current->next == NULL) {
deleteTail();
}
}
}
current = current->next;
}
}
// Delete the Head Node
template <class T>
void LinkedList<T>::deleteHead()
{
if (head != NULL) { // as long as head is not null, delete head
ListItem<T> *current = head;
head = head->next;
current->next = NULL;
head->prev = NULL;
} else {return;} // if head is null, end the function without doing anything
}
// Delete Tail Node
template <class T>
void LinkedList<T>::deleteTail()
{
ListItem<T> *tail = getTail();
tail = tail->prev;
tail->next->prev = NULL;
tail->next = NULL;
}
模板
void LinkedList::deleteElement(T项)
{
ListItem*当前=头;
列表项*温度;
如果(head==NULL){//如果列表为空,则结束函数
返回;
}
while(当前){
如果(当前->值==项目){
if(current==head){//if项目在head中
deleteHead();
}
else if(current==getTail()){//if项在尾部
deleteTail();
}
//如果项目位于两个节点之间
如果(当前!=head&¤t!=getTail()){
温度=电流;
临时->上一个->下一个=临时->下一个;
临时->下一步->上一步=临时->上一步;
当前->下一步=空;
当前->上一个=空;
如果(当前->下一步==NULL){
deleteTail();
}
}
}
当前=当前->下一步;
}
}
//删除头部节点
模板
void LinkedList::deleteHead()
{
如果(head!=NULL){//只要head不为NULL,就删除head
ListItem*当前=头;
头部=头部->下一步;
当前->下一步=空;
head->prev=NULL;
}else{return;}//如果head为null,则结束函数而不执行任何操作
}
//删除尾部节点
模板
void LinkedList::deleteTail()
{
ListItem*tail=getTail();
tail=tail->prev;
tail->next->prev=NULL;
tail->next=NULL;
}
您的代码中有几个问题。首先,在访问指针之前,您不会检查任何指针。例如,这里:
temp = current;
temp->prev->next = temp->next;
temp->next->prev = temp->prev;
如果列表中只有一个元素,则其next
和prev
成员可能为空。这意味着试图将某些内容分配给temp->prev->next
或temp->next->prev
将是访问冲突
这同样适用于其他地方,包括while
循环末尾的这一行:
current = current->next;
在那个阶段,current
可能会被删除,这意味着尝试访问其下一个成员将失败。但由于另一个问题,目前它可能不会失败
非常重要的是,您实际上没有删除任何内容。C++没有垃圾回收器,所以不能只设置一个原始指针为null并忘记它。您必须对其调用delete
,以销毁和取消分配对象,否则会导致内存泄漏。您需要在整个代码中解决这个问题,然后可能需要修改所有函数。您需要非常小心,不要在对象被删除后访问它
话虽如此,您应该真正使用智能指针(即std::shared_ptr
),而不是使用原始指针。当没有其他对象具有指向该对象的指针时,它们会为您删除该对象。您仍然需要避免访问已删除的对象,但这会使编码更简单,希望更现代/更健壮。建议:
步骤1-将成员变量ListItem*tail
添加到类ListItem
步骤2-将对getTail()
的所有调用替换为tail
步骤3-在功能删除元素中,您可以替换:
else if (current != head && current != tail)
current->next = NULL;
current->prev = NULL;
if (current->next == NULL)
deleteTail();
与:
步骤4-在功能删除元素中,您应该替换:
else if (current != head && current != tail)
current->next = NULL;
current->prev = NULL;
if (current->next == NULL)
deleteTail();
与:
步骤#5-重写函数deleteHead
,如下所示:
ListItem<T>* current = head;
if (head == tail)
head = tail = NULL;
else
head = head->next;
delete current;
ListItem<T>* current = tail;
if (tail == head)
tail = head = NULL;
else
tail = tail->prev;
delete current;
我答对了。这是我的数据结构作业中的一个问题。下面是我实现的代码。是的,我知道它有冗余和低效,但我必须在任务框架内工作
这是我的deleteElement()函数:
template <class T>
void LinkedList<T>::deleteElement(T item)
{
ListItem<T>* current = head;
ListItem<T>* temp;
if (head == NULL) { // if list is empty end the function
return;
}
while (current) {
if (current->value == item) {
if (current == head) { // if item is in the head
deleteHead();
}
else if (current == getTail()) { // if item is in the tail
deleteTail();
}
else if (current != head && current != getTail()) {
// if item is between two nodes
temp = current;
temp->prev->next = temp->next;
temp->next->prev = temp->prev;
current->next = NULL;
current->prev = NULL;
if (current->next == NULL) {
deleteTail();
}
}
}
current = current->next;
}
}
模板
void LinkedList::deleteElement(T项)
{
ListItem*当前=头;
列表项*温度;
如果(head==NULL){//如果列表为空,则结束函数
返回;
}
while(当前){
如果(当前->值==项目){
if(current==head){//if项目在head中
deleteHead();
}
else if(current==getTail()){//if项在尾部
deleteTail();
}
如果(当前!=head&¤t!=getTail()){
//如果项目位于两个节点之间
温度=电流;
临时->上一个->下一个=临时->下一个;
临时->下一步->上一步=临时->上一步;
当前->下一步=空;
当前->上一个=空;
如果(当前->下一步==NULL){
deleteTail();
}
}
}
当前=当前->下一步;
}
}
您是否尝试调试代码?可能在deleteHead()
中使用head=head->next
如果列表只包含一个元素,则必须为NULL
,在本例中为head->prev=NULL代码>将崩溃。