* Collection/LinkedList.js
/**
* Created by Mch on 8/26/18.
*/
function Node(e) {
this.element = e;
this.next = null;
}
function LinkedList() {
this.length = 0;
this.head = null;
}
LinkedList.prototype = {
append: function(element) {
var node = new Node(element), current;
if (this.head === null) {
this.head = node;
} else {
current = this.head;
while (current.next) {
current = current.next;
}
current.next = node;
}
this.length++;
},
insert: function(position, element) {
if (position <0 || position > this.length) {
return false;
}
var node = new Node(element),
current = this.head,
previous,
index = 0;
if (position === 0) {
node.next = current;
this.head = node;
} else {
while (index++ < position) {
previous = current;
current = current.next;
}
node.next = current;
previous.next = node;
}
this.length++;
return true;
},
removeAt: function(position) {
if (position <0 || position > this.length) {
return null;
}
var current = this.head,
previous,
index = 0;
if (position=== 0) {
this.head = current.next;
} else {
while (index++ < position) {
previous = current;
current = current.next;
}
previous.next = current.next;
}
this.length--;
return current.element;
},
remove: function(element) {
var index = this.indexOf(element);
return this.removeAt(index);
},
indexOf: function(element) {
var current = this.head,
index = -1;
while (current) {
if (element === current.element) {
return index;
}
index++;
current = current.next;
}
return -1;
},
isEmpty: function() {
return this.length === 0;
},
size: function() {
return this.length;
},
toString: function() {
var current = this.head,
string = '';
while (current) {
string += current.element + ", ";
current = current.next;
}
return string;
},
print: function() {
console.log(this.toString());
},
getHead: function() {
return this.head;
}
};
exports.LinkedList = LinkedList;
* Collection/HashTable.js
/**
* Created by Mch on 8/26/18.
*/
var LinkedList = require('./LinkedList').LinkedList;
function KeyValuePair(key, value) {
this.key = key;
this.value = value;
}
KeyValuePair.prototype.toString = function() {
return '['+ this.key +'-'+ this.value +']';
};
function HashTable() {
this.table = [];
}
// 2 hash functions
var hash = {
loselose: function(key) {
var hash = 0;
for (var i = 0; i < key.length; i++) {
hash += key.charCodeAt(i);
}
return hash % 37;
},
djb2: function(key) {
var hash = 5381;
for (var i = 0; i < key.length; i++) {
hash = hash * 33 + key.charCodeAt(i);
}
return hash % 1013;
}
};
// pick a hash function
HashTable.hashCode = hash.loselose;
HashTable.prototype = {
// 分离链接
put: function(key, value) {
var pos = HashTable.hashCode(key);
if (this.table[pos] === undefined) {
this.table[pos] = new LinkedList();
}
this.table[pos].append(new KeyValuePair(key, value));
},
get: function(key) {
var pos = HashTable.hashCode(key);
if (this.table[pos] !== undefined) {
var current = this.table[pos].getHead();
while (current.next) {
if (current.element.key === key) {
return current.element.value;
}
current = current.next;
}
if (current.element.key === key) {
return current.element.value;
}
}
return undefined;
},
remove: function(key) {
var position = HashTable.hashCode(key);
if (this.table[position] !== undefined) {
var current = this.table[position].getHead();
while (current.next) {
if (current.element.key === key) {
this.table[position].remove(current.element);
if (this.table[position].isEmpty()) {
this.table[position] = undefined;
}
return true;
}
}
// 检查是否为第一个或最后一个元素
if (current.element.key === key) {
this.table[position].remove(current.element);
if (this.table[position].isEmpty()) {
this.table[position] = undefined;
}
return true;
}
}
return false;
},
// TODO: 线性探查
print: function() {
for (var i = 0; i < this.table.length; ++i) {
if (this.table[i] !== undefined) {
console.log(i + ": " + this.table[i]);
}
}
}
};
exports.HashTable = HashTable;
* TestHashTable.js
var HashTable = require('./Collection/HashTable').HashTable;
function TestHashTable() {}
TestHashTable.main = function() {
var hash = new HashTable();
hash.put('Gandalf', 'gandalf@email.com');
hash.put('John', 'johnsnow@email.com');
hash.put('Tyrion', 'tyrion@email.com');
hash.put('Aaron', 'aaron@email.com');
hash.put('Donnie', 'donnie@email.com');
hash.put('Ana', 'ana@email.com');
hash.put('Jonathan', 'jonathan@email.com');
hash.put('Jamie', 'jamie@email.com');
hash.put('Sue', 'sue@email.com');
hash.put('Mindy', 'mindy@email.com');
hash.put('Paul', 'paul@email.com');
hash.put('Nathan', 'nathan@email.com');
hash.print();
console.log(hash.get('Sue'));
};
TestHashTable.main();
$ node ./TestHashTable.js
5: [Jonathan-jonathan@email.com], [Jamie-jamie@email.com], [Sue-sue@email.com],
10: [Nathan-nathan@email.com],
13: [Donnie-donnie@email.com], [Ana-ana@email.com],
16: [Tyrion-tyrion@email.com], [Aaron-aaron@email.com],
19: [Gandalf-gandalf@email.com],
29: [John-johnsnow@email.com],
32: [Mindy-mindy@email.com], [Paul-paul@email.com],
sue@email.com
线性探测法:
https://blog.csdn.net/fareast_mzh/article/details/82120675
常见的Hash函数: