开开心心学链表1(链表题总结)

目录

1、二进制链表转整数

2、删除链表中的节点

3、移除链表元素

 4、合并有序链表

5、链表的中间节点

6、删除链表中的重复元素

写在最后


1、二进制链表转整数

原题链接:1290. 二进制链表转整数 - 力扣(LeetCode) (leetcode-cn.com)

思路:先准备一个 ans 来保存结果,从头开始遍历该链表,因为这个链表的值只有0和1,所以每到一个新节点就执行该操作 ans+root.val,ans加上 root.val 之后左移一位。当链表遍历一遍之后直接return ans/2 即可,之所以要除以2是因为我们多进行了一步左移操作,加链表的最后一个结点的时候不需要再左移了,所以我们在最终结果的基础上除以2。

代码如下:

class Solution {
    public int getDecimalValue(ListNode head) {
        int ans = 0;
        while(head != null) {
            ans += head.val;
            ans <<= 1;
            head = head.next;
        }
        return ans/2;
    }
}

2、删除链表中的节点

原题链接:237. 删除链表中的节点 - 力扣(LeetCode) (leetcode-cn.com)

思路:将下一个节点的数据拷贝到需要删除节点。我们在这里其实是动了一点小聪明,因为我们删除的结点并不是题目所要求的的那个结点,而是他的下一个结点,如图所示,题目是想让我们删除①结点,我们是将②结点的数据传给①结点,然后删除掉②结点。

代码如下:

class Solution {
    public void deleteNode(ListNode node) {
        node.val = node.next.val;
        node.next = node.next.next;
        
    }
}

3、移除链表元素

原题链接:203. 移除链表元素 - 力扣(LeetCode) (leetcode-cn.com)

 思路:

1. 首先判断 head 是否为空,如果 head 为空则直接返回

2. 判断 head 的 val 是否和 要删除的 val 相等,如果相等的话,则 head = head.next,直到 head 的val 与所要删除的 val 不相等或者链表遍历结束

3. 定义两个结点,一个快结点 fast,一个慢结点 slow,slow 紧跟在 fast 后面,fast 用来找要删除的结点,找到需要删除的结点后删除该结点即可。

代码如下:

class Solution {
    public ListNode removeElements(ListNode head, int val) {
        if(head == null) return null;
        while(head != null && head.val == val ) head = head.next;
        ListNode fast = head;
        ListNode slow = null;
        while(fast != null) {
            if(fast.val == val) {
                slow.next = fast.next;
                fast = fast.next;
            }else {
                slow = fast;
                fast = fast.next;
            }
            
        }
        return head;
    }
}

法二:

 4、合并有序链表

原题链接:21. 合并两个有序链表 - 力扣(LeetCode) (leetcode-cn.com)

思路:

1. 判断是否存在空链表,如果存在直接返回另一个非空链表即可

2. 定义两个结点 head 和 tail 用来遍历新合并的链表

3. 比较 l1 和 l2 的值,我们先假设 l1.val < l2.val(不管 l1 和 l2 谁大谁小,处理方式都是一样的),此时又有两种情况:

        a. head 为 null 时,此时我们只需要 head = l1,并且 tail = l1,这样就找到了合并之后的新链表的头结点

        b. head 不为 null 是,此时,我们只需要 tail.next = l1, tail = l1,这样就把新找到的结点插入到了新的链表的尾部

重复上述步骤即可,直到一个链表遍历完毕

4. 将剩余没有遍历完的链表添加到 tail 的后面,组成完成的合并链表

 非递归代码如下:

class Solution {
    public ListNode mergeTwoLists(ListNode l1, ListNode l2) {
        if(l1 == null) return l2;
        if(l2 == null) return l1;
        ListNode head = null;
        ListNode tail = null;
        while(l1 != null && l2 != null) {
            if(l1.val < l2.val) {
                if(head == null) {
                    head = l1;
                    tail = l1;
                } else {
                    tail.next = l1;
                    tail = l1;
                }
                l1 = l1.next;
            } else {
                if(head == null) {
                    head = l2;
                    tail = l2;
                } else {
                    tail.next = l2;
                    tail = l2;
                }
                l2 = l2.next;
            }
        }
        if(l1 != null) {
            tail.next = l1;
        }
        if(l2 != null) {
            tail.next = l2;
        }
        return head;
    }
}

递归代码如下:

class Solution {
    public ListNode mergeTwoLists(ListNode l1, ListNode l2) {
        if(l1 == null) return l2;
        if(l2 == null) return l1;
        if(l1.val < l2.val) {
            l1.next = mergeTwoLists(l2,l1.next);
            return l1;
        }else {
            l2.next = mergeTwoLists(l1,l2.next);
            return l2;
        }
    }
}

5、链表的中间节点

原题链接:876. 链表的中间结点 - 力扣(LeetCode) (leetcode-cn.com)

 思路:定义两个指针,一个fast,一个slow,slow每次走一个节点,fast一次走两个节点,fast走完的时候slow正好走到链表中间。

代码如下:

class Solution {
    public ListNode middleNode(ListNode head) {
        ListNode fast = head;
        ListNode slow = head;
        while(fast != null && fast.next != null) {
            fast = fast.next.next;
            slow = slow.next;
        }
        return slow;

    }
}

6、删除链表中的重复元素

原题链接:83. 删除排序链表中的重复元素 - 力扣(LeetCode) (leetcode-cn.com)

 思路:

1. 首先判断 head 是否为 null 或者 head.next 是否为 null,二者如果有一个为 null 则直接返回就可以了

2. 定义两个结点 fast 和 slow,slow 紧跟在 fast 后面,如果 fast.val和 slow.val 相等,slow 则跳过 fast 结点,指向 fast.next,然后重新进行比较。

代码如下:

class Solution {
    public ListNode deleteDuplicates(ListNode head) {
        if(head == null || head.next == null) return head;
        ListNode fast = head.next;
        ListNode slow = head;
        while(fast != null) {
            if(slow.val == fast.val) {
                slow.next = fast.next;
                fast = fast.next;
            }else {
                slow = fast;
                fast = fast.next;
            }
        }
        return head;
    }
}

写在最后

以上就是本篇文章全部内容,作者知识水平有限,若有什么错误或者需改进之处希望大家指出,若是你有更好的代码希望能给博主留言,博主希望能在CSDN与各位一起进步,感谢大家观看!

评论 56
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值