Java 如何删除双链接列表中的尾部?
我的老师指导我们如何删除双链接列表的尾部。他为我们创建了一个循序渐进的过程或算法。我遵循了它,但它不起作用。或者也许我看错了。这是算法 检查列表是否为空Java 如何删除双链接列表中的尾部?,java,constructor,linked-list,double,tail,Java,Constructor,Linked List,Double,Tail,我的老师指导我们如何删除双链接列表的尾部。他为我们创建了一个循序渐进的过程或算法。我遵循了它,但它不起作用。或者也许我看错了。这是算法 检查列表是否为空 如果不是空的 检查列表中是否只有一个节点 如果只有一个节点,请将head和tail引用设置为null 如果有多个节点 创建一个指向下一个尾部的试探性邮件(tail.prev) 将尾部的上一个和下一个设置为null 将TENTAIL值指定给尾部 这是我的代码 public void delTail(){ Do
- 如果不是空的
- 检查列表中是否只有一个节点
- 如果只有一个节点,请将head和tail引用设置为null
- 如果有多个节点
- 创建一个指向下一个尾部的试探性邮件(tail.prev)
- 将尾部的上一个和下一个设置为null
- 将TENTAIL值指定给尾部
- 检查列表中是否只有一个节点
public void delTail(){
DoubleNode temp;
if(isEmpty()){
return;
}
else if(!isEmpty()){
if(head == tail){
head = tail = null;
}
else{
temp = tail.next;
tail.prev = null;
temp.next = null;
temp = tail;
}
}
}
这就是我看到的错误
我想我是对的还是错的?非常感谢您的帮助:)
这是我的构造函数*
public class DoubleNode{
public DoubleNode prev;
public int data;
public DoubleNode next;
public DoubleNode(int d){
this(null, d, null);
}
public DoubleNode(DoubleNode p, int d, DoubleNode n){
prev = p;
data = d;
next = n;
}
}
public class operator{
DoubleNode head;
DoubleNode tail;
DoubleNode laman;
String output = "";
public operator(){
head = tail = null;
}
public boolean isEmpty(){
return head == null;
}
public void addHead(int i){
if(isEmpty()){
head = tail =new DoubleNode(i);
}
else{
head = new DoubleNode(null, i, head);
head.prev = head;
}
}
public void addTail(int i){
DoubleNode last = new DoubleNode(i);
if(isEmpty()){
head = tail = new DoubleNode(i);
}
else{
tail.next = last;
tail = last;
}
}
public void delHead(){
DoubleNode temp = head.next;
if(head==tail){ //this if condition is testing if the head and tail is one only,
head = tail =null; //if there is only one this will set the tail and head to null
}
else{
head = head.next;
head = temp;
}
}
public void delTail(){
DoubleNode temp;
if(isEmpty()) {
return;
}
else {
if(head != tail) {
tail = tail.prev;
temp = tail;
}
else {
head = tail = null;
}
}
}
public void display(){
DoubleNode tmp = head;
output = "<html>";
for(tmp = head; tmp != null; tmp = tmp.next){
output = output + "<br>" + tmp.data + "<b>" + "<br>";
}
output = output + "</html>";
}
}
这是mt整个操作员代码*
public class DoubleNode{
public DoubleNode prev;
public int data;
public DoubleNode next;
public DoubleNode(int d){
this(null, d, null);
}
public DoubleNode(DoubleNode p, int d, DoubleNode n){
prev = p;
data = d;
next = n;
}
}
public class operator{
DoubleNode head;
DoubleNode tail;
DoubleNode laman;
String output = "";
public operator(){
head = tail = null;
}
public boolean isEmpty(){
return head == null;
}
public void addHead(int i){
if(isEmpty()){
head = tail =new DoubleNode(i);
}
else{
head = new DoubleNode(null, i, head);
head.prev = head;
}
}
public void addTail(int i){
DoubleNode last = new DoubleNode(i);
if(isEmpty()){
head = tail = new DoubleNode(i);
}
else{
tail.next = last;
tail = last;
}
}
public void delHead(){
DoubleNode temp = head.next;
if(head==tail){ //this if condition is testing if the head and tail is one only,
head = tail =null; //if there is only one this will set the tail and head to null
}
else{
head = head.next;
head = temp;
}
}
public void delTail(){
DoubleNode temp;
if(isEmpty()) {
return;
}
else {
if(head != tail) {
tail = tail.prev;
temp = tail;
}
else {
head = tail = null;
}
}
}
public void display(){
DoubleNode tmp = head;
output = "<html>";
for(tmp = head; tmp != null; tmp = tmp.next){
output = output + "<br>" + tmp.data + "<b>" + "<br>";
}
output = output + "</html>";
}
}
公共类运算符{
双结点头;
双节尾;
双节点拉曼;
字符串输出=”;
公共运营商(){
头=尾=空;
}
公共布尔值为空(){
返回头==null;
}
公共无效地址(int i){
if(isEmpty()){
头部=尾部=新的双节点(i);
}
否则{
head=新的双节点(null,i,head);
head.prev=头;
}
}
公共无效地址(int i){
DoubleNode last=新的DoubleNode(i);
if(isEmpty()){
头部=尾部=新的双节点(i);
}
否则{
tail.next=last;
尾=最后一个;
}
}
公海{
DoubleNode温度=head.next;
if(head==tail){//如果head和tail仅为一,则此if条件正在测试,
head=tail=null;//如果只有一个,则会将tail和head设置为null
}
否则{
head=head.next;
压头=温度;
}
}
公共无效delTail(){
双节点温度;
如果(isEmpty()){
返回;
}
否则{
如果(头!=尾){
tail=tail.prev;
温度=尾部;
}
否则{
头=尾=空;
}
}
}
公共空间显示(){
双节点tmp=头部;
输出=”;
for(tmp=head;tmp!=null;tmp=tmp.next){
输出=输出+“
”+tmp.data++“
”;
}
输出=输出+“”;
}
}
这是我到目前为止的全部代码,我有一个带有jframe的主类,但我认为它很好,因为我也将它用于单链接列表。但是我在双链接列表中确实遇到了一个问题,关于删除最后一个节点的问题,您的问题是您只是分配给
temp
,但实际上并没有使用它。此外,您没有正确地将链接设置回上一个元素
假设tail.next
指向head
,您可以再次执行以下操作:
tail.prev.next = tail.next; //you might need to check for `tail.prev` being null
tail.next.prev = tail.prev; //you might need to check for `tail.next` being null
//delete tail
举例说明:
A -next-> Tail -next-> Head
^---prev--+ ^---prev--+
步骤1:
+----next--------------V
A Tail -next-> Head
^---prev--+ ^---prev--+
步骤2:
+----next--------------V
A Tail -next-> Head
^---prev--+ |
^--------------prev----+
实际上,如果
tail.next==head
删除尾部与删除任何其他节点没有区别。您的else
块中有两个错误:
- 您永远不会更改
引用。最后一条语句实际上应该是尾部
的赋值tail
- 您似乎假设
有一个非空的tail
引用,但这是一个矛盾。尾部应该是最后一个节点,因此其next
引用将始终为空(除非您应该创建循环列表)。因此,next
将为null,语句temp
将触发null指针异常temp.next=tail
更有趣的属性是它的tail
属性,它指的是在删除当前tail节点后将成为prev
的节点。你的作业中明确提到了这个tail
tail.prev
else{
temp=tail.prev;//I您的代码以什么方式不起作用?您看到了什么错误或问题?代码段与DLL tail中的伪代码不匹配。next始终为null(请记住tail在末尾,因此没有next)。删除尾部时,tail.prev
实际上指向您现在想要的尾部。因此,tail=tail.prev;tail.next=null;
似乎是您所需要的一切。temp
永远不会被使用-除非您想保存旧的tail
,以便您可以清除它的“prev”以帮助垃圾收集。确实如此我的if-else条件有效吗?这就是问题所在吗?我尝试了我在这里提出的所有建议,但都不起作用。请注意,您添加的代码中还有许多其他错误:1)您有双重赋值,如head=head.next;head=temp;
2)您并不总是维护prev
和next
correc注意,当删除节点时,需要将节点.prev.next
指向节点.next
和节点.next.prev
指向节点.prev
。当插入节点时,还需要调整引用:节点.next=after.next;节点.prev=after;节点.next.prev=after;节点.next.prev=node;
(
之后的将是您插入之后的节点)。你还需要考虑当你只有一个节点时你会做什么:是否应该head==tail
为真?是否应该head.next==head
和head.prev==head
为真?如果不是,那么你需要处理那个特殊情况。我试着按照你的指示去做?但是你能检查我上面的If和else条件吗?是太多还是太多是否需要我的代码?@Bianxzy这取决于你是否真的希望头和尾相互指向。如果是这样,你基本上只需要以下检查:头==null
(在这种情况下tai
tail.next = last;
tail = last;
tail.next = last;
last.prev = tail; // needed!
tail = last;
head = temp;
head = head.next;
head.prev = null;