学习js数据结构与算法-链表(7)

97 阅读2分钟

这是我参与2022首次更文挑战的第17天,活动详情查看:2022首次更文挑战」。

个人觉得要想进大厂,就必须学习了解算法和数据结构,经历了多次面试之后,也知道了算法和数据结构的重要性,所以,我也打算从今天开始,进入学习,下载了一下电子书,边看书,边跟着书的例子来敲一下代码,下面就开始总结一下对算法和数据结构的学习吧。

第十七天:继续了解链表

  • 有序链表

    有序链表是保持元素有序的链表结构。除了使用排序算法之外,我们还可以将元素插入到正确的位置来保证链表的有序性。

    如果要对插入的数据进行排序,首先我们得要构建一个对比方法

    const Compare = {
      LESS_THAN: -1,
      BIGGER_THAN: 1
    }
    function defaultCompare(a, b) {
      if(a === b) return 0
      return a < b ? Compare.LESS_THAN : Compare.BIGGER_THAN;
    }
    

    有了对比方法,我们的有序列表还是继承单向链表

    class SortedLinkedList extends LinkedList {
      constructor() {
        super()
        this.compareFn = defaultCompare
      }
    }
    

    前面我们已经有了单向列表的一些方法,有序列表可以直接利用前面的方法去构建自己的方法。

    function insert(element, index = 0) {
      if(this.isEmpty()) {
        return super.insert(element, 0)
      }
      const pos = this.getIndexNextSortedElement(element)
      return super.insert(element, pos) 
    }
    
    function getIndexNextSortedElement(element) {
      let current = this.head
      let i = 0
      for(; i < this.size(); i++) {
        const comp = this.compareFn(element, current.element)
        if(comp < Compare.LESS_THAN) {
          return i
        }
        current = current.next
      }
      return i
    }
    

    如果是空的链表的话,可以直接调用继承的insert方法,插入到第一个位置上。

    另一种情况就是链表已经存在,因为我们的有序链表不能插入任意位置,位置都是根据规则排序好插入进去的,所以我们只需要传一个element参数就好。

    首先就是得有一个方法去获取该元素应该插入的位置,原理就是从头开始找,当传入的元素的值小于当前的值,那么就直接返回这个索引,如果一直都没有找到,那么找个i也加到了最后,也是直接返回这个索引就好。

    找到索引之后,和插入第一个元素一样,直接调用继承的insert方法。

  • 创建StackLinkedList类

    我们还可以使用LinkedList类去构建起他数据结构,例如栈、队列和双向队列。

    • 下面就用链表实现栈

      class StackLinkedList {
        constructor() {
          this.items = new DoublyLinkedList()
        }
        push() {
          this.items.push(element)
        }
        pop() {
          if(this.isEmpty()) return null
          this.item.removeAt(this.size() - 1)
        }
      }
      

      对于栈,我们会向链表尾部添加元素,也会从链表尾部移除元素。所以使用了双向链表,因为双向链表最后一个元素有尾指针,无须迭代整个链表的元素就能获取它。双向链表可以直接获取头尾的元素,减少过程的小号,它的时间复杂度和原始的Stack实现相同,为O(1)