【若川视野 x 源码共读】第32期 | yocto-queue队列链表

130 阅读2分钟

前言

本文参加了由公众号@若川视野 发起的每周源码共读活动,点击了解详情一起参与。

queue是什么

queue是一个队列链表数据的处理方法,用来处理大量数据的pushshift操作。

数据结构

学习过数据结构的,对这个了解比较轻松,简单说一下常见的数据结构吧。

常见的数据结构包含**栈****队列****链表****数组**

栈结构是我们常见的一种数据结构,只能在一端进行数据的插入和删除操作,按照先进后出(FILO)的原则存储数据,类似后来者居上,就像我们想杯子里倒水和喝水一样,先倒进杯子的水底部,喝水的时候先喝后到进来的水。

队列

队列结构,是按照先进先出,后进后出(FIFO)的原则存储数据,只能在队首操作(读取、删除等),队尾添加。类似我们排队买东西。

链表

链表结构,通常是由一连串节点组成,每个节点包含任意的实例数据和用来指向下一个节点的位置引用,是不连续的,用指针对数据进行访问。这个类似于我们要组装一列火车,每节车厢在不同的地方进行生产,组装的时候,我们按照一定顺序进行排列。

node节点的结构

image.png

链表的结构

image.png

数组

数组使我们经常使用的数据结构,就不细说了。

数组VS队列链表

在此处,我们主要对别一下这数组和单链表的pushshift操作吧。

队列链表按照队列的原则,只能队首操作,队尾添加,push和shift操作的时间复杂度为O(1)。

数组可以进行任何位置的操作,灵活度高。push操作的时间复杂度为O(1),可是shift操作的时间复杂度为O(n)。

queue如何使用

npm install yocto-queue
import Queue from 'yocto-queue';

const queue = new Queue();

queue.enqueue('🦄');
queue.enqueue('🌈');

console.log(queue.size);
//=> 2

console.log(...queue);
//=> '🦄 🌈'

console.log(queue.dequeue());
//=> '🦄'

console.log(queue.dequeue());
//=> '🌈'

源码

class Node {
	value;
	next;

	constructor(value) {
		this.value = value;
	}
}

export default class Queue {
	#head;
	#tail;
	#size;

	constructor() {
		this.clear();
	}

	enqueue(value) {
		const node = new Node(value);

		if (this.#head) {
			this.#tail.next = node;
			this.#tail = node;
		} else {
			this.#head = node;
			this.#tail = node;
		}

		this.#size++;
	}

	dequeue() {
		const current = this.#head;
		if (!current) {
			return;
		}

		this.#head = this.#head.next;
		this.#size--;
		return current.value;
	}

	clear() {
		this.#head = undefined;
		this.#tail = undefined;
		this.#size = 0;
	}

	get size() {
		return this.#size;
	}

	* [Symbol.iterator]() {
		let current = this.#head;

		while (current) {
			yield current.value;
			current = current.next;
		}
	}
}

总结

学会了队列链表的类实现的方法,顺带补充了查下对数据结构的了解。