代码随想录算法训练营42期day03

203.移除链表元素

思路一:在原链表上直接删除

代码:

/**
 * Definition for singly-linked list.
 * function ListNode(val, next) {
 *     this.val = (val===undefined ? 0 : val)
 *     this.next = (next===undefined ? null : next)
 * }
 */
/**
 * @param {ListNode} head
 * @param {number} val
 * @return {ListNode}
 */
var removeElements = function(head, val) {
    // 删除头结点
    while (head !== null && head.val === val) {
        head = head.next;
    }
    if (head === null) return head;
    // 删除非头部节点
    let pre = head, cur = head.next;
    while (cur) {
        if (cur.val === val) {
            pre.next = cur.next;
        } else {
            pre = pre.next;
        }
        cur = cur.next;
    }
    return head;
};

思路二:创建虚拟头结点

代码:

/**
 * Definition for singly-linked list.
 * function ListNode(val, next) {
 *     this.val = (val===undefined ? 0 : val)
 *     this.next = (next===undefined ? null : next)
 * }
 */
/**
 * @param {ListNode} head
 * @param {number} val
 * @return {ListNode}
 */
var removeElements = function(head, val) {
    // 创建虚拟头节点
    const data = new ListNode(0, head);
    // 删除节点
    let cur = data;
    while (cur.next) {
        if (cur.next.val === val) {
            cur.next = cur.next.next;
        } else {
            cur = cur.next;
        }
    }
    return data.next;

};

707.设计链表

class LinkNode {
    constructor(val, next) {
        this.val = val;
        this.next = next;
    }
}

var MyLinkedList = function() {
    this.size = 0;
    this.head = null;
    this.tail = null;
};

/** 
 * @param {number} index
 * @return {number}
 */
MyLinkedList.prototype.getNode = function(index) {
    // 超出链表范围
    if (index < 0 || index >= this.size) return null;
    // 创建虚拟头结点
    let cur = new LinkNode(0, this.head);
    // 查找 直到index减为0跳出循环
    while (index >= 0) {
        cur = cur.next;
        index--;
    }
    return cur;
};

MyLinkedList.prototype.get = function(index) {
    if(index < 0 || index >= this.size) return -1;
    return this.getNode(index).val;
}

/** 
 * @param {number} val
 * @return {void}
 */
MyLinkedList.prototype.addAtHead = function(val) {
    // 创建要插入的新节点
    const node = new LinkNode(val, this.head);
    // 修改原头节点指针
    this.head = node;
    // 链表为空的情况下,头结点也是尾结点
    if (!this.tail) {
        this.tail = node;
    }
    this.size++;
};

/** 
 * @param {number} val
 * @return {void}
 */
MyLinkedList.prototype.addAtTail = function(val) {
    // 创建要插入的新节点
    const node = new LinkNode(val, null);
    this.size++;
    // 当tail指针不为空时,修改指针指向
    if (this.tail) {
        this.tail.next = node;
        this.tail = node;
        return;
    }
    // 当tail指针为空即链表为空时,头结点也是尾结点
    this.head = node;
    this.tail = node; // 尾指针始终指向链表最后一个结点
};

/** 
 * @param {number} index 
 * @param {number} val
 * @return {void}
 */
// 在链表中的第 index个节点之前添加值为 val的节点。
// 如果 index等于链表的长度,则该节点将附加到链表的末尾。如果 index大于链表长度,则不会插入节点。如果 index小于0,则在头部插入节点。
MyLinkedList.prototype.addAtIndex = function(index, val) {
    if (index === this.size) {
        this.addAtTail(val);
        return;
    }
    if (index > this.size) return;
    if (index <= 0) {
        this.addAtHead(val);
        return;
    }
    // 正常情况
    // 获取插入位置的前一个 node
    const curNode = this.getNode(index-1);
    // 新节点的指针指向当前插入位置的节点
    let node = new LinkNode(val, curNode.next);
    // 插入位置的前一个node的指针指向新节点
    curNode.next = node;
    this.size++;
};

/** 
 * @param {number} index
 * @return {void}
 */
// 如果索引 index有效,则删除链表中的第 index个节点。
MyLinkedList.prototype.deleteAtIndex = function(index) {
    // 索引值无效
    if (index < 0 || index >= this.size) return;
    // 删除头结点
    if (index === 0) {
        this.head = this.head.next;
        // 如果删除的这个节点同时是尾节点,要处理尾节点
        if (index === this.size-1) {
            this.tail = this.head;
        }
        this.size--;
        return;
    }
    // 正常情况
    const node = this.getNode(index-1);
    node.next = node.next.next;
    // 删除尾结点
    if (index === this.size-1) {
        this.tail = node;
        node.next = null;
    }
    this.size--;
};

206.反转链表

思路:双指针法

代码:

/**
 * Definition for singly-linked list.
 * function ListNode(val, next) {
 *     this.val = (val===undefined ? 0 : val)
 *     this.next = (next===undefined ? null : next)
 * }
 */
/**
 * @param {ListNode} head
 * @return {ListNode}
 */
var reverseList = function(head) {
    if (!head || !head.next) return head;
    let temp = null, pre = null, cur = head;
    while (cur) {
        // 存储下一个节点
        temp = cur.next;
        // 改变指针指向
        cur.next = pre;
        // 移动pre和cur指针
        pre = cur;
        cur = temp;
    }
    // 此时temp = cur = null
    return pre;
};

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值