JS实现链表|青训营笔记

78 阅读3分钟

这是我参与「第四届青训营 」笔记创作活动的第3天

今天在牛客网刷算法,碰到一题,反转链表,当时直接懵了,因为数据结构的基础不牢固,而前端面试经常问到一些重要算法或是数据结构,为此整理了一下,在这里做个记录,方便以后查看。

1.题目长这样

给定一个单链表的头结点pHead(该头节点是有值的,比如在下图,它的val是1),长度为n,反转该链表后,返回新链表的表头。 数据范围: 0≤n≤1000 要求:空间复杂度 O(1) ,时间复杂度 O(n) 。 如当输入链表{1,2,3}时,经反转后,原链表变为{3,2,1},所以对应的输出为{3,2,1}。

2.解决方法

那既然学的是前端,就用js来实现一下吧,顺便练习一下js的一些方法。 考虑到js是动态语言,没有指针,那么链表的数据域和指针域将通过构造函数来模拟。当然解决这道题的话不需要构造函数模拟整个链表的创建过程,只需要给出核心代码即可。

思路大概是这样,如果要反转链表,那么先假设这个链表只有三个数据,中间的那个记为current,他的前一个节点记作pre,后一个节点记作next,反转时只需要将current的指针域指向pre,然后交换pre,current和current,next两个节点对应的数据域即可;因此代码如下:

function ReverseList(pHead){
    //如果链表为空,直接返回空表
    if(!pHead) return null;
    //假定当前节点为头节点
    let cur=pHead;
    let pre=null;
    //当pre不为null时,反转完成;
    while(pre){
    let next=cur.next;
    cur.next=pre;
    pre=cur;
    cur=next;
    }
    return pre;
}

js实现链表

既然做了这题,那就顺便把链表的一些方法也实现一遍吧。

首先构造两个类,一个用来创建节点,一个是链表的完整实现,将创建的节点组合成链表。代码如下:

class Node{
    constructor(data){
        this.data=data;
        this.head=null;
    }
}

class List{
    constructor(){
    this.len=0;
    this.head=null;
    }
}

整体结构大概是这样,剩下的就是在List类中添加增删改查的一些方法:

  1. 首先是添加节点的操作,需要指出的是,添加时需要指明位置,即在链表的什么位置添加,因此insert方法接受两个参数,一个是插入的位置的索引,另一个是插入的元素,代码如下:

insert(index,node){
    if(index<0||index>this.len)throw new Error('插入位置不合法');
    let ele=new Node(node);
    if(index==0){
        node.next=this.head;
        this.head=node;
    }else{
    //调用getpos方法返回当前节点的前一个节点
        let pre=this.getpos(index-1);
        node.next=pre.next;
        pre.next=node;
    }
    this.len++;
}
getpos(index){
    if(index<0||index>=this.len)throw new Error('查找的元素不存在!');
    for(let i=0;i<index;i++){
    let cur=this.head;
    cur.next=cur;
    }
    return cur;
}

2.删除操作,代码如下:


delnode(index){
 if(index<0||index>this.len)throw new Error('指定元素不存在,删除失败!');
 
 let cur=this.head;
 if(index==0){
     this.head=cur.next;
 }else{
     let pre=this.getpos(index-1);
     cur=pre.next;
     pre.next=cur.next;
 }
 this.len--;
}

3.查找元素,代码如下:

search(ele){
let cur=this.head;
for(let i=0;i<this.len;i++){
    if(cur===ele){
    return i;
    }
    return new Error('查找的元素不存在!')
  }
}

ok,先记录到这里吧。