所以我在夏天的OO课程中,我们需要编写一个函数来从链表中间删除一个节点。我很亲密,但有一些问题。我的代码成功遍历链表,但是一旦循环找到节点,实际上就会删除节点。到目前为止,这是我的功能:
template< class NODETYPE >
bool List< NODETYPE >::removeMiddle( NODETYPE &value, int i )
{
ListNode <NODETYPE> * tempPtr = firstPtr;
ListNode <NODETYPE> * prevPtr ;
int counter=1;
if ( isEmpty() )
return false;
if (i <= 0)
return false;
while (tempPtr != 0 && counter < i){
counter++;
if ( firstPtr == lastPtr )
firstPtr = lastPtr = 0;
else
firstPtr = firstPtr->nextPtr;
prevPtr = tempPtr;
tempPtr = tempPtr->nextPtr;
}
if (counter == i){
value = tempPtr->data; // data being removed
delete tempPtr;
}
}
return true;
RecordCounter--;
}
答案 0 :(得分:3)
您忘记更改上一个节点,使其不再指向您删除的节点。
你想要的东西(很大程度上)与:
相似if ( counter == i-1 ) //next node is the one you want to delete
{
aux = tempPtr->nextPtr->nextPtr; //retain next next node
delete tempPtr->nextPtr; //delete next node
tempPtr->nextPtr = aux; //current node now points to the node after the deleted one
}
答案 1 :(得分:2)
我没有任何具体细节的第一个猜测是你没有保持列表的完整性。虽然我在C ++上非常生疏。
您正在删除tempPtr并跟踪prevPtr ...但删除后不会重新链接列表的两半。
prevPtr->nextPtr = tempPtr->nextPtr
答案 2 :(得分:0)
您忘记调整列表中的链接。 delete
之后节点仍在那里,但现在它无效。哎呀!
此功能很有用:
NODETYPE* unlink( NODETYPE*& pNode )
{
NODETYPE* const result = pNode;
pNode = pNode->nextPtr;
return result;
}
将其称为传递指向您要删除的节点的nextPtr
。您返回指向节点的指针,重新链接列表,以便节点不再在列表中。现在您可以delete
该节点。
如果您只有一个指针直接指向要删除的节点,并且该列表是单链接的,该怎么办?嗯,唐纳德克努特曾经问过他的“计算机编程艺术”(如果我没记错的话)。一种解决方案是将数据与下一个节点交换,然后删除下一个节点。