一 关于链表的一些练习题
1.删除链表中等于给定值 val 的所有节点。
题目的链接:. - 力扣(LeetCode)
class Solution {
public ListNode removeElements(ListNode head, int val) {
if (head == null) {
return null;
}
// 使用虚拟节点来处理头节点可能需要被删除的情况
ListNode dummy = new ListNode(-1);
dummy.next = head;
ListNode cur = head;
ListNode pre = dummy;
while (cur != null) {
if (cur.val == val) {
pre.next = cur.next;
} else {
pre = cur;
}
cur = cur.next;
}
return dummy.next;
}
}

2.反转一个单链表
题目的链接:. - 力扣(LeetCode)
class Solution {
public ListNode reverseList(ListNode head) {
if(head==null){
return head;
}
ListNode cur=head.next;
head.next=null;
while (cur!=null){
ListNode curN= cur.next;
cur.next=head;
head=cur;
cur=curN;
}
return head;
}
}


3.给定一个带有头结点 head 的非空单链表,返回链表的中间结点。如果有两个中间结点,则返回第二个中间结点。
题目链接:. - 力扣(LeetCode)
class Solution {
public ListNode middleNode(ListNode head) {
if(head==null){
return head;
}
ListNode fast=head;
ListNode slow=head;
while (fast!=null && fast.next!=null){
fast=fast.next.next;
slow=slow.next;
}
return slow;
}
}
这道题运用了小学数学概念相同的路程,fast的速度时slow速度的两倍,所以slow用的时间为fast的两倍,一个已经走完,一个正好在中间。

4.. 输入一个链表,输出该链表中倒数第k个结点。
让fast前往前走k个节点,然后fast和slow同时走,当fast走到最后一个节点时,slow走的节点就是倒数第K个节点。
public int returnNode(int key) {
ListCode fast=head;
ListCode slow=head;
if (head==null){
return -1;
}
int count=0;
while (count!=key-1){
fast=fast.next;
if(fast==null){
return -1;
}
count++;
}
while (fast.next!=null){
fast=fast.next;
slow=slow.next;
}
return slow.val;
}
}
5. 将两个升序链表合并为一个新的 升序 链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。
题目链接:21. 合并两个有序链表 - 力扣(LeetCode)
class Solution {
public ListNode mergeTwoLists(ListNode headA, ListNode headB) {
ListNode newHead=new ListNode(-1);
ListNode tem=newHead;
while (headA!=null && headB!=null){
if(headA.val<headB.val){
tem.next=headA;
headA=headA.next;
}else {
tem.next=headB;
headB=headB.next;
}
tem=tem.next;
}
if(headA!=null){
tem.next=headA;
}else {
tem.next=headB;
}
return newHead.next;
}
}
public static void main(String[] args) {
MySingleList list1=new MySingleList();
MySingleList list2=new MySingleList();
MySingleList.ListCode newHead=mergeTwoLists(list1.head,list2.head);
}
}


6. . 编写代码,以给定值x为基准将链表分割成两部分,所有小于x的结点排在大于或等于x的结点之前 。
题目链接:链表分割_牛客题霸_牛客网
public class Partition {
public ListNode partition(ListNode pHead, int x) {
ListNode be=null;
ListNode bs=null;
ListNode ae=null;
ListNode as=null;
ListNode cur=pHead;
while (cur != null) {
if(cur.val<x){
if (bs == null) {
be=bs=cur;
}else {
be.next=cur;
be=be.next;
}
}else {
if (as==null){
ae=as=cur;
}else {
ae.next=cur;
ae=ae.next;
}
}
cur=cur.next;
}
if(bs==null){
return as;
}
be.next=as;
if(as!=null){
ae.next=null;
}
return bs;
}
}


7.链表的回文结构
题目链接:链表的回文结构_牛客题霸_牛客网
public boolean chkPalindrome() {
if (head==null){
return true;
}
ListCode fast=head;
ListCode slow=head;
while (fast!=null && fast.next!=null){
fast=fast.next.next;
slow=slow.next;
}
ListCode cur=slow.next;
while (cur!=null){
ListCode curN=cur.next;
cur.next=slow;
slow=cur;
cur=curN;
}
while (head.next!=slow) {
if (head.val != slow.val) {
return false;
}
if(head.next==slow){
return true;
}
head=head.next;
slow=slow.next;
}
return true;
}
}
注:这个题的主要难点是如果它有奇数个或者偶数个时,它的情况是不同的。
第一步:找到中间的位置

第二步:对slow后进行反转
第三步:判断值是否相同
第四步:判断奇偶

8.输入两个链表,找出它们的第一个公共结点。
题目链接:. - 力扣(LeetCode)
public class Solution {
public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
ListNode pl=headA;
ListNode ps=headB;
int lenA=0;
int lenB=0;
while(pl!=null){
pl=pl.next;
lenA++;
}
while(ps!=null){
ps=ps.next;
lenB++;
}
int len=lenA-lenB;
pl=headA;
ps=headB;
if(len<0){
pl=headB;
ps=headA;
len=lenB-lenA;
}
while(len!=0){
pl=pl.next;
len--;
}
while(pl!=ps){
pl=pl.next;
ps=ps.next;
}
if(pl==null){
return null;
}
return pl;
}
}
9.求它们分别的长度,判断长度差,这个长度差就是出去公共部分的长度差,所以让长的链表先走长度差的大小,然后两个再同时走。


10.给定一个链表,判断链表中是否有环
题目链接:. - 力扣(LeetCode)
public boolean hasCycle(ListCode head) {
ListCode fast=head;
ListCode slow=head;
while (fast!=null &&fast.next!=null){
fast=fast.next.next;
slow=slow.next;
if (fast==slow) {
return true;
}
}
return false;
}


10.给定一个链表,返回链表开始入环的第一个节点。 如果链表无环,则返回 NULL
题目链接:. - 力扣(LeetCode)
public ListCode detectCycle() {
ListCode fast=head;
ListCode slow=head;
while (fast!=null && fast.next!=null) {
fast = fast.next.next;
slow = slow.next;
if (fast == slow) {
break;
}
}
if(fast==null || fast.next==null){
//没有环
return null;
}
slow=head;
while (fast!=slow){
fast=fast.next;
slow=slow.next;
}
return slow;
}
}


希望能对大家有所帮助!!!

链表练习题汇总及解题思路

1万+

被折叠的 条评论
为什么被折叠?



