JS数据结构与算法-链表

简介: 定义链表是由一组节点组成的集合。每个元素由一个存储元素本身的节点和一个指向下一个元素的应用(也称之为指针或链接)组成。一个链表的结构现实中的举例说明就是火车。
  1. 定义
    链表是由一组节点组成的集合。每个元素由一个存储元素本身的节点和一个指向下一个元素的应用(也称之为指针或链接)组成。


    img_1e8e32ca79aecfd9fcfbcd521d0015ce.png
    一个链表的结构

    现实中的举例说明就是火车。每节车厢是链表的元素,车厢间的连接就是指针:


    img_07800489e0e976ebd285eaf7f7d5f75d.png
    来自《学习javascript数据结构与算法》
  2. 创建一个链表

  • 定义一个LinkedList类和一个Node类
function LinkedList() {
  //定义一个Node类,element用来保存节点上的数据,next表示指向链表中下一个项的指针
  var Node = function(element) {
    this.element = element;
    this.next = null;
  }

  //用length表示列表的数量
  var length = 0;
  //head存储第一个节点的引用
  var head = null;
}
  • 实现append方法向列表尾部添加一个新的项
    有两种情况:列表为空,添加的是第一个元素,列表不为空,向其追加元素。
this.append = function(element) {
    var node = new Node(element),
        current;
    if(head === null) {
      head = node;
    }else {
      current = head;
      //循环链表,直到找到最后一项
      while(current.next) {
        current = current.next;
      }
      //找到最后一项将其next赋为node,建立连接
      current.next = node;
    }
    //更新链表长度
    length++;
  };
  • 实现removeAt方法从链表的特定位置移除一项
  this.removeAt = function(position) {
    if(position > -1 && position < length) {
      var current = head,
          previous,
          index = 0;

      //移除第一项
      if(position === 0) {
        head = current.next;
      } else {
        //循环列表,找到position位置的元素和前一个元素
        while (index++ < position) {
          previous = current;
          current = current.next;
        }
        //将previous与current的下一项链接起来:跳过current,从而移除它
        previous.next = current.next;
      }
      length--;
      return current.element;
    }else {
      return null;
    }
  };
  • 实现insert方法向列表的特定位置插入一个新的项
  //向列表的特定位置插入一个新的项
  this.insert = function(position,element) {
    if(position >= 0 && position <= length) {
      var node = new Node(element),
          current = head,
          previous,
          index = 0;

      //如果要在0的位置插入新值,那么就要将head设为新值,并将它的下一个值设为当前值
      if(position === 0) {
        node.next = current;
        head = node;
      }else {
        //循环访问列表,找到目标位置,将目标位置上的元素用previou保存;将目标位置链接的下一个元素用current保存
        while(index++ <position) {
          previous = current;
          current = current.next;
        }
        //将新元素node的next属性设置为current
        //让previous.next指向新元素node
        node.next = current;
        previous.next = node;
      }
      length++; //更新列表长度

      return true;

    }else {
      return false;
    }
  };
  • 实现indexOf方法,返回元素在列表中的索引。如果列表没有该元素则返回-1
this.indexOf = function(element) {
    var current = head,
        index = 0;

    //循环这个链表,如果找到就返回index
    while(current) {
      if(element === current.element) {
        return index;
      }
      index++;
      current = current.next;
    }
    return -1;
  };
  • 实现remove方法,从链表中移除一项
this.remove = function(element) {
    //找到这个元素的索引值
    var index = this.indexOf(element);
    return this.removeAt(index);
  };
  • isEmpty、size、toString方法
//如果链表中不包含任何元素,返回true,如果链表长度大于0则返回false。
  this.isEmpty = function() {
    return length === 0;
  };

  //返回链表的length
  this.size = function() {
    return length;
  };
  
  //把链表中的对象转换为字符串
  this.toString = function() {
    var current = head,
        string = '';

    while(current) {
      string += current.element;
      current = current.next;
    }
    return string;
  };
  • 全部代码
//定义一个LinkedList类
function LinkedList() {
  //定义一个Node类,element用来保存节点上的数据,next表示指向链表中下一个项的指针
  var Node = function(element) {
    this.element = element;
    this.next = null;
  }

  //用length表示列表的数量
  var length = 0;
  //head存储第一个节点的引用
  var head = null;

  //向列表尾部添加一个新的项
  this.append = function(element) {
    var node = new Node(element),
        current;
    if(head === null) {
      head = node;
    }else {
      current = head;
      //循环列表,直到找到最后一项 
      while(current.next) {
        current = current.next;
      }
      //找到最后一项将其next赋为node,建立连接
      current.next = node;
    }
  };

  //从列表的特定位置移除一项
  this.removeAt = function(position) {
    if(position > -1 && position < length) {
      var current = head,
          previous,
          index = 0;

      //移除第一项
      if(position === 0) {
        head = current.next;
      } else {
        while (index++ < position) {
          previous = current;
          current = current.next;
        }
        //将previous与current的下一项链接起来:跳过current,从而移除它
        previous.next = current.next;
      }
      length--;
      return current.element;
    }else {
      return null;
    }
  };

  //返回元素在列表中的索引。如果列表中没有该元素则返回-1
  this.indexOf = function(element) {
    var current = head,
        index = 0;

    //循环这个链表,如果找到就返回index
    while(current) {
      if(element === current.element) {
        return index;
      }
      index++;
      current = current.next;
    }
    return -1;
  };

  //从列表中移除一项
  this.remove = function(element) {
    //找到这个元素的索引值
    var index = this.indexOf(element);
    return this.removeAt(index);
  };

  //如果链表中不包含任何元素,返回true,如果链表长度大于0则返回false。
  this.isEmpty = function() {
    return length === 0;
  };

  this.size = function() {
    return length;
  };

  this.toString = function() {
    var current = head,
        string = '';

    while(current) {
      string += current.element;
      current = current.next;
    }
    return string;
  };
}

var test = new LinkedList();
test.append(1);
test.append(2);
test.append(4);
console.log(test.toString()); //"124"
console.log(test.indexOf(2)); // 1

参考学习

《学习javascript数据结构与算法》

目录
相关文章
|
3月前
|
算法
【❤️算法笔记❤️】-每日一刷-19、删除链表的倒数第 N个结点
【❤️算法笔记❤️】-每日一刷-19、删除链表的倒数第 N个结点
82 1
|
3月前
|
算法 索引
❤️算法笔记❤️-(每日一刷-141、环形链表)
❤️算法笔记❤️-(每日一刷-141、环形链表)
60 0
|
3月前
|
算法
【❤️算法笔记❤️】-(每日一刷-876、单链表的中点)
【❤️算法笔记❤️】-(每日一刷-876、单链表的中点)
59 0
|
3月前
|
算法
【❤️算法笔记❤️】-每日一刷-23、合并 K 个升序链表
【❤️算法笔记❤️】-每日一刷-23、合并 K 个升序链表
36 0
|
3月前
|
存储 算法
【❤️算法笔记❤️】-每日一刷-21、合并两个有序链表
【❤️算法笔记❤️】-每日一刷-21、合并两个有序链表
122 0
|
5天前
|
存储 监控 算法
局域网网络管控里 Node.js 红黑树算法的绝妙运用
在数字化办公中,局域网网络管控至关重要。红黑树作为一种自平衡二叉搜索树,凭借其高效的数据管理和平衡机制,在局域网设备状态管理中大放异彩。通过Node.js实现红黑树算法,可快速插入、查找和更新设备信息(如IP地址、带宽等),确保网络管理员实时监控和优化网络资源,提升局域网的稳定性和安全性。未来,随着技术融合,红黑树将在网络管控中持续进化,助力构建高效、安全的局域网络生态。
25 9
|
11天前
|
监控 算法 JavaScript
基于 Node.js Socket 算法搭建局域网屏幕监控系统
在数字化办公环境中,局域网屏幕监控系统至关重要。基于Node.js的Socket算法实现高效、稳定的实时屏幕数据传输,助力企业保障信息安全、监督工作状态和远程技术支持。通过Socket建立监控端与被监控端的数据桥梁,确保实时画面呈现。实际部署需合理分配带宽并加密传输,确保信息安全。企业在使用时应权衡利弊,遵循法规,保障员工权益。
25 7
|
9天前
|
存储 监控 JavaScript
深度探秘:运用 Node.js 哈希表算法剖析员工工作时间玩游戏现象
在现代企业运营中,确保员工工作时间高效专注至关重要。为应对员工工作时间玩游戏的问题,本文聚焦Node.js环境下的哈希表算法,展示其如何通过快速查找和高效记录员工游戏行为,帮助企业精准监测与分析,遏制此类现象。哈希表以IP地址等为键,存储游戏网址、时长等信息,结合冲突处理与动态更新机制,确保数据完整性和时效性,助力企业管理层优化工作效率。
23 3
|
2月前
|
算法 安全 搜索推荐
2024重生之回溯数据结构与算法系列学习之单双链表精题详解(9)【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构王道第2.3章之IKUN和I原达人之数据结构与算法系列学习x单双链表精题详解、数据结构、C++、排序算法、java、动态规划你个小黑子;这都学不会;能不能不要给我家鸽鸽丢脸啊~除了会黑我家鸽鸽还会干嘛?!!!
|
2月前
|
存储 Web App开发 算法
2024重生之回溯数据结构与算法系列学习之单双链表【无论是王道考研人还是IKUN都能包会的;不然别给我家鸽鸽丢脸好嘛?】
数据结构之单双链表按位、值查找;[前后]插入;删除指定节点;求表长、静态链表等代码及具体思路详解步骤;举例说明、注意点及常见报错问题所对应的解决方法