编程语言:C#
链表定义
* public class ListNode {
* public int val;
* public ListNode next;
* public ListNode(int val=0, ListNode next=null) {
* this.val = val;
* this.next = next;
* }
* }
题目链接:203. 移除链表元素 - 力扣(LeetCode)
题意:删除链表中等于给定值 val 的所有节点。
示例 1: 输入:head = [1,2,6,3,4,5,6], val = 6 输出:[1,2,3,4,5]
示例 2: 输入:head = [], val = 1 输出:[]
示例 3: 输入:head = [7,7,7,7], val = 7 输出:[]
思路:如果下一个节点元素值等于目标值,就将指向下一个节点的指针指向下下个节点
1.单独处理头结点:移除头结点和移除其他节点的操作是不一样的,因为链表的其他节点都是通过前一个节点来移除当前节点,而头结点没有前一个节点。所以头结点如何移除呢,其实只要将头结点向后移动一位就可以,这样就从链表中移除了一个头结点。
2.使用虚拟头结点:这样原链表的所有节点就都可以按照统一的方式进行移除了。最后在题目中,return 头结点的时候,需要 return dummyNode.next;
, 这才是新的头结点
图片来源:代码随想录代码随想录 (programmercarl.com)
public class Solution {
public ListNode RemoveElements(ListNode head, int val) {
ListNode dummyhead=new ListNode(0,head);
ListNode cur=dummyhead;
if(head==null) return null;
while(cur.next!=null){
if(cur.next.val==val){
cur.next=cur.next.next;
}else{
cur=cur.next;
}
}
return dummyhead.next;
}
}
题目链接:707. 设计链表 - 力扣(LeetCode)
题意:
在链表类中实现这些功能:
思路:巧用dummyhead,构造函数中初始化dummyhead和链表size值,add和delete元素不要忘记对size进行加减
class ListNode//链表定义
{
public int val;
public ListNode next;
public ListNode(int val) { this.val = val; }
}
public class MyLinkedList//自定义链表
{
ListNode dummyHead;
int size;
public MyLinkedList()
{
//构造函数中初始化dummyhead和size
dummyHead = new ListNode(0);
size = 0;
}
public int Get(int index)
{
if (index < 0 || size <= index) return -1;
//每个方法都要赋值一个current指针
ListNode current = dummyHead;
for (int i = 0; i <= index; i++)
{
current = current.next;
}
return current.val;
}
public void AddAtHead(int val)
{
//复用在某个位置添加元素的方法
AddAtIndex(0, val);
}
public void AddAtTail(int val)
{
AddAtIndex(size, val);
}
//在指定位置添加元素,需要位置的索引和元素值
public void AddAtIndex(int index, int val)
{
if (index > size) return;
index = Math.Max(0, index);
//大小要同步更改
size++;
ListNode current1 = dummyHead;
for (int i = 0; i < index; i++)
{
current1 = current1.next;
}
ListNode newnode = new ListNode(val);
newnode.next =current1.next;
current1.next = newnode;
}
public void DeleteAtIndex(int index)
{
if (index >= size || index < 0) return;
var current2 = dummyHead;
for (int i = 0; i < index; i++)
{
current2 = current2.next;
}
current2.next = current2.next.next;
size--;
}
}
题目链接:206. 反转链表 - 力扣(LeetCode)
题意:反转一个单链表。
示例: 输入: 1->2->3->4->5->NULL 输出: 5->4->3->2->1->NULL
思路:current指针指向当前节点,下一个节点先用一个next节点保存,然后将原本指向next的指针指向前一个节点previous,最后pre指针和cur指针向后移动一位处理下一个节点
1.普通写法
public class Solution {
public ListNode ReverseList(ListNode head) {
ListNode cur=head;
ListNode pre=null;
ListNode next=null;
while(cur!=null){
next=cur.next;
cur.next=pre;
pre=cur;
cur=next;
}
return pre;
}
}
2.递归写法
public class Solution {
public ListNode ReverseList(ListNode head) {
return Reverse(null,head);
}
public ListNode Reverse(ListNode pre,ListNode current){
ListNode tmp;
if(current==null) return pre;
tmp=current.next;
current.next=pre;
return Reverse(current,tmp);
}
}