基本数据结构和查找算法

this.find = function(item){ //查找

var currNode = this.head;

while(currNode.element != item){

if(currNode.next === this.head) return null;

currNode = currNode.next;

};

return currNode;

};

this.insert = function(newElement, item){ //在item之后插入

var newNode = new Node(newElement);

var current = this.find(item);

newNode.next = current.next;

current.next = newNode;

};

this.display = function(){ //输出列表

var currNode = this.head;

while(currNode.next !== this.head){

console.log(currNode.next.element);

currNode = currNode.next;

}

};

this.remove = function(element){ //删除

var currNode = this.head;

while(1){

if(currNode.next == this.head) return false;

if(currNode.next.element == element) break;

currNode = currNode.next;

}

currNode.next = currNode.next.next;

};

}

双向链表

function Node(element){

this.element = element;

this.next = null;

this.previous = null;

}

function LList(){

this.head = new Node(“head”);

this.tail = this.head;

this.find = function(item){ //查找

var currNode = this.head;

while(currNode.element != item){

if(currNode.next === null) return null;

currNode = currNode.next;

};

return currNode;

};

this.insert = function(newElement, item){ //在item之后插入

var newNode = new Node(newElement);

var current = this.find(item);

newNode.next = current.next;

current.next = newNode;

current.next.previous = newNode;

newNode.previous = current;

};

this.display = function(){ //输出列表

var currNode = this.head;

while(currNode.next !== null){

console.log(currNode.next.element);

currNode = currNode.next;

}

};

this.remove = function(item){ //删除

var currNode = this.find(item);

if(currNode){

currNode.previous.next = currNode.next;

currNode.next.previous = currNode.previous;

currNode.next = null;

currNode.previous = null;

return true;

}

return false;

};

this.dispReverse = function(){ //反向输出

var currNode = this.tail;

while(currNode.previous !== null){

console.log(currNode.element);

currNode = currNode.previous;

}

};

}

字典

function dictionary(){

this.dataStore = [];

this.add = function(key, value){ //插入

if(this.find(key)) console.log(“'” + key + “’ exists”);

else this.dataStore[key] = value;

};

this.find = function(key){ //查找

return this.dataStore[key];

};

this.remove = function(key){ //删除

delete this.dataStore[key];

};

this.showAll = function(){ //有序输出

var keys = Object.keys(this.dataStore).sort();

keys.forEach(function(key){

console.log(key + " -> " + this.dataStore[key]);

});

};

this.count = function(){ //计数

return Object.keys(this.dataStore).length;

};

this.clear = function(){ //清除

for(var k in this.dataStore){

if(dataStore.hasOwnPorperty(k)){

delete this.dataStore[k];

}

}

};

}

集合

function Set(){

if(arr){

this.arr = arr.filter(function(item, index) {

return arr.indexOf(item) === index;

});

} else {

this.arr = [];

}

}

Set.prototype.constructor = Set;

Myset.prototype.sort = function(fun){ //排序

this.arr.sort(fun);

return this;

};

Set.prototype.add = function(data){ //添加

if(this.dataStore.indexOf(data) < 0){

this.dataStore.push(data);

}

return this;

};

Set.prototype.show = function(){ //输出

console.log(this.dataStore.join(“,”));

return this;

};

Set.prototype.remove = function(data){ //删除

var pos = this.dataStore.indexOf(data);

if(pos > -1){

this.dataStore.splice(pos, 1);

}

return this;

};

Set.prototype.size = function(){ //得到当前集合大小(元素数量)

return this.dataStore.length;

};

Set.prototype.contains = function(data) { //是否包含data

return this.dataStore.indexOf(data) > -1;

};

Set.prototype.clone = function(){ //复制当前集合

var tempSet = new Set();

for(var i = 0; i < this.size(); ++i)

tempSet.add(this.dataStore[i]);

return tempSet;

};

Set.prototype.union = function(set){ //求并集

var tempSet = this.clone();

for(var i = 0; i < set.size(); ++i){

if(!tempSet.contains(set.dataStore[i]))

temp.dataStore.push(set.dataStore[i]);

}

return tempSet;

};

Set.prototype.interSect = function(set){ //求交集

var tempSet = new Set();

for(var i = 0; i < this.size(); ++i){

if(set.contains(this.dataStore[i]))

tempSet.add(this.dataStore[i]);

}

return tempSet;

};

Set.prototype.subSet = function(set){ //判断当前集合是否set的子集

if(this.size() > set.size()) return false;

else{

for(var i = 0; i < this.size(); ++i){

if(!set.contains(this.dataStore[i]))

return false;

}

}

return true;

};

this.difference = function(set){ //求差集 this-set

var tempSet = new Set();

for(var i = 0; i < this.dataStore.length; ++i){

if(!set.contains(this.dataStore[i]))

tempSet.add(this.dataStore[i]);

}

return tempSet;

};

哈希表

function HashTable(){

this.table = [];

//this.values = [];

//当key是整数的时候可以简单的使用simpleHash

this.simpleHash = function(data){ //这个函数下文不会用到

var total = 0;

for(var i = 0; i < data.length; ++i)

total += data.charDodeAt(i);

return total % this.table.length;

};

//simpleHash()有一个严重的问题:不同字符串可能得到相同hash码,比如"Raymond"和"Clayton"。 这叫做哈希碰撞(hashing collision)

this.betterHash = function(string, arr){

const H = 31; //引入一个质数

var total = 0;

for(var i = 0; i < string.length; ++i)

total += H * total + string.charCodeAt(i);

total = total % arr.length;

return parseInt(total);

};

this.showDistro = function(){

var n = 0;

for(var i = 0; i < this.table.length; ++i){

// if(this.table[i] !== undefined) //线性探针法使用这个if

if(this.table[i][0] !== undefined) //散列法使用这个if

console.log(i + ": " + this.table[i]);

}

};

//即使使用了betterHash,也不能保证在所有输入中不会一重复的输出,因此产生了散列法(separate chaining)和线性探针法(linear probing)

//建立散列

this.buildChains = function(){

for(var i = 0; i < this.table.length; ++i)

this.table[i] = [];

};

//散列法对应put函数

this.put = function(data){

var pos = this.betterHash(data);

var index = 0;

if(this.table[pos][index] === undefined)

this.table[pos][index] = data;

else {

while(this.table[pos][index] !== undefined) ++index;

this.table[pos][index] = data;

}

};

//散列法对应get函数

this.get = function(key){

var pos = this.betterHash(key);

var index = 0;

if(this.table[pos][index] === key)

return this.table[pos][index + 1];

else {

while(this.table[pos][index] !== key) index += 2;

return this.table[pos][index + 1];

}

return undefined;

};

/*

//线性探针法对应put函数

this.put = function(key, data){

var pos = this.betterHash(data);

if(this.table[pos] == undefined){

this.table[pos] = key;

this.values[pos] = data;

} else {

while(this.table[pos] != undefined) ++pos;

this.table[pos] = key;

this.values[pos] = data;

}

};

//线性探针法对应get函数

this.get = function(key){

var hash = -1;

hash = this.betterHash(key);

if(hash > -1){

for(var i = hash; this.table[hash] != undefined; ++i){

if(this.table[hash] == key)

return this.values[hash];

}

}

};

*/

}

function Node(data, left, right){ //树节点

this.data = data;

this.left = left;

this.right = right;

this.show = function(){ return this.data; };

}

//建立一个二叉查找树(Binary Search Tree)

function BST(){

this.root = null;

this.insert = function(data){

var n = new Node(data, null, null);

if(this.root === null) {

this.root = n;

}

else{

var current = this.root;

var parent;

while(true){

parent = current;

if(data < current.data){

current = current.left;

if(current === null){

parent.left = n;

break;

}

}

else{

current = current.right;

if(current == null){

parent.right = n;

break;

}

}

}

}

};

//中序遍历

this.inOrder = function(node){

if(node !== null){

inOrder(node.left);

console.log(node.show() + " ");

inOrder(node.right);

}

};

//前序遍历

this.preOrder = function(node){

if(node !== null){

console.log(node.show() + " ");

preOrder(node.left);

preOrder(node.right);

}

};

//后序遍历

this.postOrder = function(node){

if(node !== null){

postOrder(node.left);

postOrder(node.right);

console.log(node.show() + " ");

}

};

//得最小值

this.getMin = function(){

var current = this.root;

while(current.left !== null)

current = current.left;

return current.data;

};

//得最大值

this.getMax = function(){

var current = this.root;

while(current.right !== null)

current = current.right;

return current.data;

};

//查找值

function find(data){

var current = this.root;

while(current !== null){

if(current.data == data) return current;

else if(data < current.data) current = current.left;

else if(data > current.data) current = current.right;

}

return null;

};

//删除值

this.removeData = function(data){

this.root = removeNode(this.root, data);

function removeNode(node, data){

if(node === null) return null;

if(data === node.data){

if(node.left == null && node.right == null) return null;

if(node.left == null) return node.right;

if(node.right == null) return node.left;

var tempNode = getSmallest(node.right);

node.data = tempNode.data;

node.right = removeNode(node.right, tempNode.data);

return node;

}

else if(data < node.data){

node.left = removeNode(node.left, data);

return node;

} else{

node.right = removeNode(node.right, data);

return node;

}

}

};

}

function Graph(v_num){

this.vertices = v_num; //定点数量

this.edges = 0; //边的数量

this.adj = []; //邻接矩阵

this.marked = []; //用于遍历时标记已遍历的点

this.vertexList = []; //存放顶点

this.edgeTo = []; //在寻找最短路径时,存放轨迹

for(var i = 0; i < this.vertices; ++i){ //初始化邻接矩阵

this.adj[i] = [];

this.adj[i] = push(“”);

}

this.addEdge = function(v, w){ //添加边,传入2个点

this.adj[v].push(w);

this.adj[w].push(v);

this.edges++;

};

this.showGraph = function(){ //输出图

for(var i = 0; i < this.vertices; ++i){

console.log(i + " -> ");

for(var j = 0; j < this.vertices; ++j){

if(this.adj[i][j] !== undefined)

console.log(this.adj[i][j] + " ");

}

console.log(“\n”);

}

};

//深度优先遍历

this.dfs = function(v){

for(var i = 0; i < this.vertices; ++i) //初始化标记矩阵

this.mark[i] = false;

innerDfs(v);

function innerDfs(v){

this.marked[v] = true;

if(this.adj[v] !== undefined)

console.log(v + " ");

for(var i = 0; i < this.adj[v].length; ++i){

var ver = this.adj[v][i];

if(!this.marked[ver]) this.innerDfs(ver);

}

}

};

//广度优先遍历

this.bfs = function(s){

for(var i = 0; i < this.vertices; ++i) //初始化标记矩阵

this.mark[i] = false;

var queue = []; //存放访问过的节点

this.marked[s] = true;

queue.push(s);

while(queue.length > 0){

var v = queue.shift();

if(v !== undefined) console.log(s + “”);

for(var i = 0; i < this.adj[v].length; ++i){

var ver = this.adj[v][i];

if(!this.marked[ver]){

this.edgeTo[ver] = v;

this.marked[ver] = true;

queue.push(ver);

}

}

}

};

this.hasPathTo = function(v){ //判断是否有到节点v的路径

return this.marked[v];

};

this.showPath = function(){ //显示路径

while(paths.length > 0){

if(paths.legnth > 1) console.log(paths.pop() + ‘-’);

else console.log(paths.pop());

}

};

this.pathTo = function(v) { //计算path路径

var path = [];

var source = 0;

if(!this.hasPathTo(v))

return undefined;

for(var i = v; i !== source; i = this.edgeTo[i])

path.push(i);
ES6

  • 列举常用的ES6特性:

  • 箭头函数需要注意哪些地方?

  • let、const、var

  • 拓展:var方式定义的变量有什么样的bug?

  • Set数据结构

  • 拓展:数组去重的方法

  • 箭头函数this的指向。

  • 手写ES6 class继承。

微信小程序

  • 简单描述一下微信小程序的相关文件类型?

  • 你是怎么封装微信小程序的数据请求?

  • 有哪些参数传值的方法?

  • 你使用过哪些方法,来提高微信小程序的应用速度?

  • 小程序和原生App哪个好?

  • 简述微信小程序原理?

  • 分析微信小程序的优劣势

  • 怎么解决小程序的异步请求问题?

其他知识点面试

  • webpack的原理

  • webpack的loader和plugin的区别?

  • 怎么使用webpack对项目进行优化?

  • 防抖、节流

  • 浏览器的缓存机制

  • 描述一下二叉树, 并说明二叉树的几种遍历方式?

  • 项目类问题

  • 笔试编程题:

最后

技术栈比较搭,基本用过的东西都是一模一样的。快手终面喜欢问智力题,校招也是终面问智力题,大家要准备一下一些经典智力题。如果排列组合、概率论这些基础忘了,建议回去补一下。

  • 14
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值