206反转链表&19删除链表的倒数第n个结点 设计链表

55 阅读1分钟

206反转链表,关键是要有两个指针,一个是当前的,一个是先前的,有点滑动窗口的思想

/**
 * Definition for singly-linked list.
 * public class ListNode {
 *     int val;
 *     ListNode next;
 *     ListNode() {}
 *     ListNode(int val) { this.val = val; }
 *     ListNode(int val, ListNode next) { this.val = val; this.next = next; }
 * }
 */
class Solution {
    public ListNode reverseList(ListNode head) {
        if(head==null){
            return head;
        }
        ListNode temp;
        ListNode cur = head;
        ListNode pre = null;
        while(cur!=null){
            temp = cur.next;
            cur.next = pre;
            pre = cur;
            cur = temp;
        }
        return pre;
    }
}

class Solution {
    public ListNode removeNthFromEnd(ListNode head, int n) {
        //这道题的关键在于去想清倒数第几个和正数第几个的关系,
        //最好的方法就是拿双指针去指引。同时慢指针要跑的比快指针慢n+1步,这样就能方便做指针的删除操作
        ListNode allpre = new ListNode(0);
        allpre.next = head;
        ListNode fast = allpre;
        ListNode slow = allpre;
        while((fast!=null) && (n!=0)){
            fast = fast.next;
            n--;
        }
        // if(fast!=null){   //在这里有bug,下一个指针如果是null,java无法指向
        //     fast = fast.next;
        // }
        
        while(fast.next!=null){   //主要是这里的问题,之前没加fast.next,这样子就会导致后面,
        //fast和slow已经变成空的了,空的指针没有下一个指针了
            fast = fast.next;
            slow = slow.next;
        }
        slow.next = slow.next.next;
        return allpre.next;
        
    }
}
class ListNode{   //代码后面出错的一个问题是这里加了(),写成方法了
    int val;
    ListNode next;
    ListNode(){}   //没搞懂这一步空指针要干嘛   
    ListNode(int val){   //一个是这里没有赋值,给到int val而是直接val
        this.val = val;
    }
}

class MyLinkedList {
    int size;
    ListNode head;

    public MyLinkedList() {
        //初始化链表
        size = 0;
        head = new ListNode(0);   
    }
    
    public int get(int index) {
        if(index<0 || index>=size) {  //这里如果index等于长度,也查不到
            return -1;
        }
        ListNode cur = head;
        for (int i = 0; i<=index;i++) {
            cur = cur.next;
        }
        return cur.val;
    }
    
    public void addAtHead(int val) {
        addAtIndex(0,val);
    }
    
    public void addAtTail(int val) {
        addAtIndex(size,val);
    }
    
    public void addAtIndex(int index, int val) {
         ListNode cur = new ListNode(val);  //这样才是创建出一个节点
         if(index<0){
             index = 0;//插入头节点的意思就是令index为0
         }
         if (index>size){
             return; 
         }
         size++;
         ListNode now = head;
         for(int i = 0;i < index;i++){   //在这个范围这有点懵,到底应该是index还是index-1,没搞懂
             now = now.next;   //都赋值了,一直在head那里插入
         }
         cur.next = now.next;
         now.next = cur;     
        
        }


    
public void deleteAtIndex(int index) {
    if(index<0 || index>=size) {
        return;
    }
    size--;
    if(index == 0) {
        //没考虑index等于0,即为头结点的情况
        head = head.next;
        return;   //赋值完就相当于完成删除操作了,不需要进行后面的操作了,直接return
    }
    ListNode cur = head;
    for(int i = 0 ;i<index;i++){
        cur = cur.next;
    }
    cur.next = cur.next.next;
}
}