数据结构
-
线性表
零个或多个数据元素的有限排列 数据元素可以为空 数据元素有限 数据元素之间的逻辑接口为线性结构 数据元素类型一致
-
顺序线性表
使用连续的内存存储单元防止线性数据元素
- 数组
-
链式线性表
数据元素可以随意存储在某个存储单元 每个节点会包含其他的节点的地址
- 单向链表 ( 每个节点除了数据元素,还包含一个指向一个指向下一个节点的指针)
- 双向链表 ( 每个节点除了数据元素,还包含一个指向上一个节点的指针和一个指向下一个节点的指针)
- 静态链表 (使用顺序结构实现链式线性表)
- 循环链表
顺序线性表适合 频繁的 查找 或者知道需要的存储空间大小 链式线性表适合 插入 和 删除操作
-
实现单向链表(typeScript)
类型声明 export declare interface Link<T> { length: number;//长度 values:T[];//所有值 append(ele: T): number;//新增 setValue(index:number,value:T):void;//修改 insert(index:number,value:T):void;//插入 removeElementByIndex(index: number): T | null;//删除 removeElement(ele: T): number;//删除 getElementByIndex(index: number): T | null;//获取 getIndexByElement(ele:T):number;//获取 }
实现 import { Link } from "./Link"; namespace YoLink { class Node<T> { value: any; index: number; next: any; constructor(value: T | null, index: number, next: Node<T> | null) { this.value = value; this.index = index; this.next = next; } } export class SingLinkList<T> implements Link<T> { header: Node<T>; eleCount = 0; constructor() { this.header = new Node(null, 0, null); } static from<T>(values: T[] = []): SingLinkList<T> { const link = new SingLinkList<T>(); values.forEach(link.append.bind(link)); return link; } get length() { return this.eleCount; } set length(len: number) { if (len >= this.eleCount) return; else if (len < this.eleCount && len > 0) { var value: Node<T> = this.header; while (--len >= 0 && value != null) { value = value.next; } value.next = null; this.eleCount = len; } else { this.header.next = null; this.eleCount = 0; } } _getElement(index: number): Node<T> | null {//内部方法 便于获取对应索引的节点 var count = index + 1; var node: Node<T> = this.header; while (--count >= 0 && node != null) { node = node.next; } return node; } _resetIndex() {//内部方法 重置索引 var count = this.eleCount; var node = this.header; var index = -1; while (count-- > 0) { node = node.next; node.index = ++index; } } append(ele: T): number { var node = this._getElement(this.eleCount - 1); const nextNode = new Node<T>(ele, this.eleCount, null); node.next = nextNode; this.eleCount += 1; return this.eleCount; } getElementByIndex(index: number): T { const node = this._getElement(index); return node ? node.value : null; } getIndexByElement(ele: T): number { var node = this.header; while (node != null) { if (node.value == ele) { return node.index; } node = node.next; } return -1; } removeElementByIndex(index: number): T | null { var node = this._getElement(index); if (node == null || node == this.header) { return null; } else { if (node.index == 0) { this.header.next == this._getElement(1); } else if (node.index == this.eleCount - 1) { this._getElement(index - 1).next = null; } else { this._getElement(index - 1).next = this._getElement(index + 1); } this.eleCount -= 1; this._resetIndex(); } } removeElement(ele: T): number { if (ele == null) return -1; var node = this.header; while (node != null && node.next.value != ele) { node = node.next; } if (node == null) return -1; const index = node.next.index; var selectNode = node.next; if (index == 0) { this.header.next = selectNode; } else { node.next = selectNode.next; } this.eleCount -= 1; this._resetIndex(); // this.deleteElementByIndex(index); return index; } setValue(index: number, value: T) { const node = this._getElement(index); if (node) { node.value = value; } } insert(index: number, value: T) { const node = this._getElement(index); if (node) { const next = node.next; const newNode = new Node(value, index, next); node.next = newNode; } else if (index == this.eleCount) { const newNode = new Node(value, index, null); const last = this._getElement(this.eleCount - 1); last.next = newNode; } else { return; } this.eleCount += 1; this._resetIndex(); } get a(): number { return this.eleCount; } get values(): T[] { const values: T[] = []; var node = this.header.next; if (node == null) return values; do { values.push(node.value); } while ((node = node.next) != null); return values; } } }
测试 const singLink2: Link<number> = new YoLink.SingLinkList(); singLink2.append(1); singLink2.append(2); singLink2.append(3); singLink2.append(4); console.log(singLink2.values); singLink2.removeElement(3); console.log(singLink2.getElementByIndex(2)); singLink2.setValue(2, 100); singLink2.insert(1, 66); singLink2.insert(30, 99999); console.log(singLink2.values); singLink2.length = 2; console.log(singLink2.values); const singLink3 = YoLink.SingLinkList.from([1, 2, 4, 5, 6]); console.log(singLink3.values);
-