Java双链表删除方法



我的问题是我的delete方法没有删除我想要删除的节点,并给我一个无限循环。

public void delete(String name){
Node current = head;
boolean checker = false;
while(current != null && current.name != name && checker != true){
try{
if(current.name.equals(name)){
Node p = current.previous;
Node q = current.next;
/*The code can somehow get through only above this line, below here its not anymore*/
p.next = q;
q.previous = p;
System.out.println("Item successfully deleted.");
checker = true;
}else if(!current.name.equals(name) && current == tail){
System.out.println("Item not found.");
}
current = current.next;
} catch(NullPointerException e){}          
}
}

我来这里是想请教一下我的问题(抱歉我英语不好(

您正在检查是否已到达列表current == tail的末尾,但没有突破它。您可以在else if中添加break语句。

除此之外,您正在使用==来比较字符串。我不知道你为什么在那里添加它,它可以被删除。此外,您必须(几乎总是(从不捕获NullPointerException。

"无限循环";意味着你的循环条件不正确,你没有在每次迭代中取得进展,或者你的数据有一个循环。您同时使用current==null和current==tail来表示它是最后一个元素。选择一种方式。建议您重写循环条件,只处理迭代,如果正文中有匹配项,则使用带中断的条件:

for(current = head; current; current = current.next) {
if(current.name.equals(name)) {
if(current == head)
head = current.next
else
current.previous.next = current.next; 
if(current == tail)
tail = current.previous;
else
current.next.previous = current.previous;
break;
}
// if tail.next is not initialized to null
// if(current == tail) break;
}

我在这里看到了一个没有副作用的潜在无限循环。如果列表中包含node.name设置为null的节点,则调用current.name.equals(name)会导致NullPointerException。如果您位于列表的任一端,则下一个或上一个指针将为null,这也将导致相同的异常。此异常被捕获并丢弃。请注意,这会阻止当前指针的前进,从而导致发生相同的迭代。至少,即使你没有采取任何其他行动,也要确保打印出异常。它将有助于调试。

你的while循环条件过于复杂。while(current != null)应该足够了,因为:

使用if(current.name.equals(name))消除了对current.name!=的需要名称另外,不要使用==或!=用于字符串比较。这是一个指针比较。大多数equals方法都处理指针比较。

在此处使用break或return进行流控制,并删除checker布尔值。tail.next应始终指向null以表示列表的末尾。我看到checker布尔值的唯一原因是delete是否应该删除所有匹配的节点,并且你想知道它是否至少发生过一次。从我在代码中看到的情况来看,情况并非如此。

我会把它重写为:

public void delete(String name){
Node current = head;
while(current != null){
try{
if(current.name.equals(name)){
...
return;
// Do not advance current here. Refer to finally block below.
}
} catch(NullPointerException e){
e.printStackTrace();
return; // If function should stop on error.
} finally {current = current.next;} // This prevents the repeat as it always happens.
}
System.out.println("Item not found.");
}

请注意,如果您使用";中断";而不是";返回";则";找不到项目"行将始终打印。你必须用if语句和flag来保护它。

public void delete(String name){
Node current = head;
while(current != null){
if(current.name.equals(name)){
if(current.prev != null){
current.prev.next = current.next
}
if(current.next != null){
current.next.prev = current.prev
}
System.out.println("Removed node")
break;
}
current = current.next;
}
}

如果节点为非null,则可以使用此逻辑删除与名称匹配的节点(给定名称始终存在(。

相关内容

最新更新