1.链表创建不需确定大小,增加和删除元素效率高,查找慢。
2.链表就像一个火车,车厢保存元素(人),链接指向下一个车厢
3.链表中的常见操作:
- append(element):向链表尾部添加一个新的项;
- insert(position,element):向链表的特定位置插入一个新的项;
- get(position):获取对应位置的元素;
- indexOf(element):返回元素在链表中的索引。如果链表中没有该元素就返回-1;
- update(position,element):修改某个位置的元素;
- removeAt(position):从链表的特定位置移除一项;
- remove(element):从链表中移除一项;
- isEmpty():如果链表中不包含任何元素,返回trun,如果链表长度大于0则返回false;
- size():返回链表包含的元素个数,与数组的length属性类似;
- toString():由于链表项使用了Node类,就需要重写继承自JavaScript对象默认的toString方法,让其只输出元素的值;
4.单向链表封装,head的类型和节点是一样的
function Linklist() {
//封装节点
function Node(data) {
this.data = data;
this.next = null;
}
//链表属性,head的类型和节点是一样的
this.head = null;
this.length = 0;
}
5.append方法实现,关键判断节点是否是第一个
//一.append方法实现
Linklist.prototype.append = function (data) {
//1.首先创建一个节点,用传进来的data
var newNode = new Node(data);
//2.判断是不是第一个节点
if(this.length == 0){
//头指针指向节点
this.head = newNode;
}else {
//需要遍历找到尾节点的指针,指向它
var current = this.head;
while(current.next){
current = current.next;
}
current.next = newNode;
}
//3.节点长度+1
this.length += 1;
}
6.toString
//二.toString方法实现
Linklist.prototype.toString = function () {
//遍历链表,依次打印.
var listString = '';
var current = this.head;
while (current){
listString += current.data + ' '
current = current.next;
}
return listString;
}
7.insert.插入的参数是(position,data),还是要分在第0个位置插入和其他位置插入的情况
位置和索引都是从0开始的,代表第一个节点。用current进行遍历。index=position的时候,到达插入的位置。
但前面还需要用一个pre保存前一个节点
//三.insert方法实现
Linklist.prototype.insert = function (position,data) {
//1.判断position越界,等于长度正好插在尾部
if(position <0 || position > this.length) return false;
//2.创建节点
var newNode = new Node(data);
//3.当position等于0时,插入0号位置
if(position == 0){
//待插点先指向原先的第一个点
newNode.next = this.head;
this.head = newNode;
}else {
var index = 0;
var current = this.head;
var previous = null;
//注意这里是先判断index是不是小于position,然后再+1
while(index++ < position){
previous = current;
current = current.next;
}
previous.next = newNode;
newNode.next = current;
}
//4.长度+1
this.length += 1;
return true;
}
8.get方法实现
//四.get方法实现
Linklist.prototype.get = function (position) {
//1.越界判断,注意这里等于length也不行哦,那个位置是空的
if(position < 0 || position >= this.length) return null;
//2.获取相应的data,注意index先判断,再++
var index = 0;
var current = this.head;
while(index++ < position) {
current = current.next;
}
return current.data
}
9.indexOf方法实现,这里我if里的==写成=了,导致错误
//五.indexOf方法实现
Linklist.prototype.indexOf = function (data) {
var index = 0;
var current = this.head;
//只要current存在就一直往后找
while(current) {
if(current.data == data) {
return index;
}
current = current.next;
index += 1;
}
//遍历完了,说明没有找到
return -1;
}
10.update方法和get很像,先查找,在修改。第一步都是要判断position越界问题。
//六.update方法,和get很像
Linklist.prototype.update = function (position, newdata) {
if (position < 0 || position >= this.length) return false;
var index = 0;
var current = this.head;
while (index++ < position) {
current = current.next;
}
//找到后修改
current.data = newdata;
return true;
}
11.removeAt,要分删除第一个节点和其他节点的情况
//七.removeAt方法
Linklist.prototype.removeAt = function (position) {
if (position < 0 || position >= this.length) return null;
//需要index索引, previous ,current指针
var index = 0;
var current = this.head;
var previous = null;
//要分删除第一个节点和其他节点的情况
if(position == 0){
this.head = this.head.next
}else{
while(index++ < position) {
previous = current;
current = current.next;
}
previous.next = current.next;
}
//链表长度-1
this.length -= 1;
//返回被删除的元素
return current.data;
}
12.remove(data),可以先get索引到位置,再removeAt
//八.remove方法
Linklist.prototype.remove = function (data) {
//1.获取位置
var position = this.indexOf(data);
//2.删除对应位置数据
return this.removeAt(position);
}
13.isEmpty
//九.isEmpty方法
Linklist.prototype.isEmpty = function () {
return this.length == 0;
}
14.链表大小
//十.size方法
Linklist.prototype.size =function () {
return this.length;
}