磁力吧,苏州景点,春晚节目单-小二狗,互撩社区,男男女女单生信息,有趣的新闻

admin 2019-07-14 阅读:235

一、html和css部分

1、怎么了解CSS的盒子模型?

规范盒子模型:宽度=内容的宽度(content)+ border + padding
低版本IE盒子模型:宽度=内容宽度(content+border+padding)

2、BF

* 什么是 BFC

BFC(Block Formatting Context)格式化上下文,是 Web 页面中盒模型布局的 CSS 烘托办法,指一个独立的烘托区域或许说是一个阻隔的独立容器。

* 构成 BFC 的条件

* 起浮元素,float 除 none 以外的值

* 定位元素,position(absolute,fixed)

* display 为以下其间之一的值 inline-block,table-cell,table-caption

* overflow 除了 visible 以外的值(hidden,auto,scroll)

* BFC 的特性

* 内部的 Box 会在笔直方向上一个接一个的放置。

* 笔直方向上的间隔由 margin 决议

* bfc 的区域不会与 float 的元素区域堆叠。

* 核算 bfc 的高度时,起浮元素也参加核算

* bfc 便是页面上的一个独立容器,容器里边的子元素不会影响外面元素。

3、怎么铲除起浮?

不清楚起浮会发作高度陷落:起浮元素父元素高度自适应(父元素不写高度时,子元素写了起浮后,父元素会发作高度陷落)

* clear铲除起浮(增加空div法)在起浮元素下方增加空div,并给该元素写css款式:{clear:both;height:0;overflow:hidden;}

* 给起浮元素父级设置高度

* 父级一同起浮(需求给父级同级元素增加起浮)

* 父级设置成inline-block,其margin: 0 auto居中办法失效

* 给父级增加overflow:hidden 铲除起浮办法

* 全能铲除法 after伪类 清起浮(现在干流办法,引荐运用)

.float_div:after{

content:".";

clear:both;

display:block;

height:0;

overflow:hidden;

visibility:hidden;

}

.float_div{

zoom:1

}

4、用纯CSS创立一个三角形的原理是什么?

span {
width: 0;
height: 0;
border-top: 40px solid transparent;
border-left: 40px solid transparent;
border-right: 40px solid transparent;
border-bottom: 40px solid #ff0000;
}



5、css3完结0.5px的细线?

/* css */
.line {
position: relative;
}
.line:after {
content: "";
position: absolute;
left: 0;
top: 0;
width: 100%;
height: 1px;
background-color: #000000;
-webkit-transform: scaleY(.5);
transform: scaleY(.5);
}
/* html */

6、css完结三栏布局

左右固定,中心自适应。



(1)flex办法









.box {
display: flex;
justify-content: center;
height: 200px;
}
.left {
width: 200px;
background-color: red;
height: 100%;
}
.content {
background-color: yellow;
flex: 1;
}
.right {
width: 200px;
background-color: green;
}










(2)肯定定位办法

Document

.box {

position: relative;

height: 200px;

}

.left {

width: 200px;

background-color: red;

left: 0;

height: 100%;

position: absolute;

}

.content {

background-color: yellow;

left: 200px;

right: 200px;

height: 100%;

position: absolute;

}

.right {

width: 200px;

background-color: green;

right: 0;

height: 100%;

position: absolute;

}

(3)起浮办法







Document

.box {
height: 200px;
}
.left {
width: 200px;
background-color: red;
float: left;
height: 100%;
}
.content {
background-color: yellow;
height: 100%;
}
.right {
width: 200px;
background-color: green;
float: right;
height: 100%;
}










7、让一个div笔直居中



(1)宽度和高度已知的







Document

.box {
width: 400px;
height: 200px;
position: relative;
background: red;
}
.content {
width: 200px;
height: 100px;
position: absolute;
top: 50%;
left: 50%;
margin-left: -100px;
margin-top: -50px;
background: green;
}








(2)宽度和高度不知道







Document

.box {
width: 400px;
height: 200px;
position: relative;
background: red;
}
.content {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
background: green;
}








(3)flex布局







Document

.box {
width: 400px;
height: 200px;
background: red;
display: flex;
justify-content: center;
align-items: center;
}
.content {
width: 200px;
height: 100px;
background: green;
}








二、JS

1、闭包

闭包概念

能够读取其他函数内部变量的函数。
或简略了解为界说在一个函数内部的函数,内部函数持有外部函数内变量的引证。

闭包用处

1、读取函数内部的变量
2、让这些变量的值一向保持在内存中。不会再f1调用后被主动铲除。
3、便利调用上下文的局部变量。利于代码封装。
原因:f1是f2的父函数,f2被赋给了一个大局变量,f2一向存在内存中,f2的存在依靠f1,因而f1也一向存在内存中,不会在调用完毕后,被废物收回机制收回。

闭包缺陷

1、由于闭包会使得函数中的变量都被保存在内存中,内存耗费很大,所以不能乱用闭包,不然会形成网页的功能问题,在IE中或许导致内存走漏。处理办法是,在退出函数之前,将不运用的局部变量悉数删去。

2、闭包会在父函数外部,改动父函数内部变量的值。所以,假如你把父函数当作方针(object)运用,把闭包当作它的共用办法(Public Method),把内部变量当作它的私有特色(private value),这时一定要当心,不要随意改动父函数内部变量的值。

闭包运用场景

闭包运用场景之setTimeout



闭包运用场景之回调



2、js中函数履行

在 ES5.1 里边函数是这样履行的(不评论use strict和一些特殊情况,JS好杂乱的),按如下次序履行:

1. 承认“this”的值 (切当的来说,this在JS里边不是一个变量名而是一个关键字)
2. 创立一个新的作用域
3. 处理形参/实参(没有界说过才声明,无论怎么都从头赋值,没有对应实参则赋值为"undefined"):
关于每一个传入的实参,依照从左往右的次序顺次履行:假如对应的形参在本作用域中还没有界说,则在本作用域中声明形参,并赋值。假如现已界说过了,则从头给其赋值。(没有对应实参则赋值为"undefined")(没有界说:便是“没有声明”的意思)
4. 处理函数界说(没有界说过才声明,无论怎么都从头赋值):
对该函数中一切的界说的函数,依照代码写的次序顺次履行:假如这个变量名在本作用域中还没有界说,则在本作用域中声明这个函数名,而且赋值为对应的函数,假如界说了这个变量,在可写的情况下从头给这个变量赋值为这个函数,不然抛出反常。
5. 处理 "arguments"(没有界说过才声明和赋值):
假如在本作用域中没有界说 arguments,则在本作用域中声明arguments并给其赋值。
6. 处理变量声明(没有界说过才声明,不赋值):
关于一切变量声明,依照代码写的次序顺次履行:假如在本作用域中没有界说这个变量,则在本作用域中声明这个变量,赋值为undefined
7. 然后履行函数代码。(当然是去变量界说里边的 var 履行)

3、new一个方针的进程中发作了什么嘛

1. 创立空方针;
var obj = {};
2. 设置新方针的constructor特色为结构函数的称号,设置新方针的__proto__特色指向结构函数的prototype方针;
obj.__proto__ = ClassA.prototype;
3. 运用新方针调用函数,函数中的this被指向新实例方针:
ClassA.call(obj);//{}.结构函数();
4. 将初始化完毕的新方针地址,保存到等号左面的变量中

4、宏使命跟微使命

  • macro-task(宏使命):包含全体代码script,setTimeout,setInterval
  • micro-task(微使命):Promise,process.nextTick


5、防抖和节省

归纳运用场景

  • 防抖(debounce):便是指触发工作后在 n 秒内函数只能履行一次,假如在 n 秒内又触发了工作,则会从头核算函数履行时刻。
  • search查找联想,用户在不断输入值时,用防抖来节省恳求资源。
  • window触发resize的时分,不断的调整浏览器窗口大小会不断的触发这个工作,用防抖来让其只触发一次
  • 节省(throttle):便是指接连触发工作可是在 n 秒中只履行一次函数。节省会稀释函数的履行频率。
  • 鼠标不断点击触发,mousedown(单位时刻内只触发一次)
  • 监听翻滚工作,比方是否滑到底部主动加载更多,用throttle来判别 所谓防抖,便是指触发工作后在 n 秒内函数只能履行一次,假如在 n 秒内又触发了工作,则会从头核算函数履行时刻。

防抖函数分为非当即履行版和当即履行版。

  • 非当即履行版的意思是触发工作后函数不会当即履行,而是在 n 秒后履行,假如在 n 秒内又触发了工作,则会从头核算函数履行时刻。
  • 当即履行版的意思是触发工作后函数会当即履行,然后 n 秒内不触发工作才干持续履行函数的作用。
/**
* @desc 函数防抖
* @param func 函数
* @param wait 推迟履行毫秒数
* @param immediate true 表当即履行,false 表非当即履行
*/
function debounce(func,wait,immediate) {
let timeout;
return function () {
let context = this;
let args = arguments;
if (timeout) clearTimeout(timeout);
if (immediate) {
var callNow = !timeout;
timeout = setTimeout(() => {
timeout = null;
}, wait)
if (callNow) func.apply(context, args)
}
else {
timeout = setTimeout(function(){
func.apply(context, args)
}, wait);
}
}
}

所谓节省,便是指接连触发工作可是在 n 秒中只履行一次函数。节省会稀释函数的履行频率。

关于节省,一般有两种办法能够完结,分别是时刻戳版和定时器版。

  • 时刻戳版的函数触发是在时刻段内开端的时分
  • 定时器版的函数触发是在时刻段内完毕的时分。
/**
* @desc 函数节省
* @param func 函数
* @param wait 推迟履行毫秒数
* @param type 1 表时刻戳版,2 表定时器版
*/
function throttle(func, wait ,type) {
if(type===1){
let previous = 0;
}else if(type===2){
let timeout;
}
return function() {
let context = this;
let args = arguments;
if(type===1){
let now = Date.now();
if (now - previous > wait) {
func.apply(context, args);
previous = now;
}
}else if(type===2){
if (!timeout) {
timeout = setTimeout(() => {
timeout = null;
func.apply(context, args)
}, wait)
}
}
}
}

6、数组的常用办法

改动原数组的办法

  • splice() 增加/删去数组元素
语法:arrayObject.splice(index,howmany,item1,.....,itemX)
参数:
1.index:必需。整数,规则增加/删去项意图方位,运用负数可从数组结尾处规则方位。
2.howmany:可选。要删去的项目数量。假如设置为 0,则不会删去项目。
3.item1, ..., itemX:可选。向数组增加的新项目。
回来值: 假如有元素被删去,回来包含被删去项意图新数组。
  • sort() 数组排序
语法:arrayObject.sort(sortby)
参数:
1.sortby 可选。规则排序次序。有必要是函数。。
回来值: 回来包排序后的新数组。
  • pop() 删去一个数组中的最终的一个元素
语法:arrayObject.pop()
参数:无
回来值: 回来被删去的元素。
  • shift() 删去数组的第一个元素
语法:arrayObject.shift()
参数:无
回来值: 回来被删去的元素。
  • push() 向数组的结尾增加元素
语法:arrayObject.push(newelement1,newelement2,....,newelementX)
参数:
1.newelement1 必需。要增加到数组的第一个元素。
2.newelement2 可选。要增加到数组的第二个元素。
3.newelementX 可选。可增加若干个元素。
回来值: 回来被删去的元素。
  • unshift() 向数组的最初增加一个或更多元素
语法:arrayObject.unshift(newelement1,newelement2,....,newelementX)
参数:
1.newelement1 必需。要增加到数组的第一个元素。
2.newelement2 可选。要增加到数组的第二个元素。
3.newelementX 可选。可增加若干个元素。
回来值: arrayObject 的新长度。。
  • reverse() 倒置数组中元素的次序
语法:arrayObject.reverse()
参数:无
回来值: 倒置后的新数组。
  • copyWithin() 指定方位的成员仿制到其他方位
语法:array.copyWithin(target, start = 0, end = this.length)
参数:
1.target(必需):从该方位开端替换数据。假如为负值,表明倒数。
2.start(可选):从该方位开端读取数据,默以为 0。假如为负值,表明倒数。
3.end(可选):到该方位前中止读取数据,默许等于数组长度。假如为负值,表明倒数。
回来值: 回来当时数组。
  • fill() 填充数组
语法:array.fill(value, start, end)
参数:
1.value 必需。填充的值。
2.start 可选。开端填充方位。
3.end 可选。中止填充方位 (默以为 array.length)
回来值: 回来当时数组。

不改动原数组的办法

  • slice() 浅仿制数组的元素
语法:array.slice(begin, end);
参数:
1.begin(可选): 索引数值,承受负值,从该索引处开端提取原数组中的元素,默许值为0。
2.end(可选):索引数值(不包含),承受负值,在该索引处前完毕提取原数组元素,默许值为数组结尾(包含最终一个元素)。
回来值: 回来一个从开端到完毕(不包含完毕)挑选的数组的一部分浅仿制到一个新数组方针,且原数组不会被修正。
  • join() 数组转字符串

语法:array.join(str)

参数:

1.str(可选): 指定要运用的分隔符,默许运用逗号作为分隔符。

回来值: 回来生成的字符串。

  • concat() 兼并两个或多个数组
语法:var newArr =oldArray.concat(arrayX,arrayX,......,arrayX)
参数:
1.arrayX(有必要):该参数能够是具体的值,也能够是数组方针。能够是恣意多个。
回来值: 回来回来兼并后的新数组。
  • indexOf() 查找数组是否存在某个元素
语法:array.indexOf(searchElement,fromIndex)
参数:
1.searchElement(有必要):被查找的元素
2.fromIndex(可选):开端查找的方位(不能大于等于数组的长度,回来-1),承受负值,默许值为0。
回来值: 回来下标
  • lastIndexOf() 查找指定元素在数组中的最终一个方位
语法:arr.lastIndexOf(searchElement,fromIndex)
参数:
1.searchElement(有必要): 被查找的元素
2.fromIndex(可选): 逆向查找开端方位,默许值数组的长度-1,即查找整个数组。
回来值: 办法回来指定元素,在数组中的最终一个的索引,假如不存在则回来 -1。(从数组后边往前查找)
  • includes() 查找数组是否包含某个元素
语法:array.includes(searchElement,fromIndex=0)
参数:
1.searchElement(有必要):被查找的元素
2.fromIndex(可选):默许值为0,参数表明查找的开端方位,承受负值。正值超越数组长度,数组不会被查找,回来false。负值肯定值超越长数组度,重置从0开端查找。
回来值: 回来布尔

7、当即履行函数

声明一个匿名函数,立刻调用这个匿名函数。意图是保护内部变量不受污染。

(function(n1, n2) {
console.log("这是匿名函数的自履行的第一种写法,成果为:" + (n1 + n2))
})(10, 100);
(function start(n1, n2) {
console.log("这是函数声明办法的自履行的第一种写法,成果为:" + (n1 + n2))
})(10, 100);
(function(n1, n2) {
console.log("这是匿名函数的自履行的第二种写法,成果为:" + (n1 + n2))
}(10, 100));
(function start(n1, n2) {
console.log("这是函数声明办法的自履行的第二种写法,成果为:" + (n1 + n2))
}(10, 100));

8、js原型和原型链

每个方针都会在其内部初始化一个特色,便是prototype(原型),当咱们拜访一个方针的特色时,假如这个方针内部不存在这个特色,那么他就会去prototype里找这个特色,这个prototype又会有自己的prototype,所以就这样一向找下去,也便是咱们平常所说的原型链的概念。

联系:instance.constructor.prototype = instance.proto

特色:JavaScript方针是经过引证来传递的,咱们创立的每个新方针实体中并没有一份归于自己的原型副本,当咱们修正原型时,与之相关的方针也会承继这一改动。当咱们需求一个特色时,JavaScript引擎会先看当时方针中是否有这个特色,假如没有的话,就会查找它的prototype方针是否有这个特色,如此递推下去,共同检索到Object内建方针。

function Func(){}
Func.prototype.name = "汪某";
Func.prototype.getInfo = function() {
return this.name;
}
var person = new Func();
console.log(person.getInfo());//"汪某"
console.log(Func.prototype);//Func { name = "汪某", getInfo = function() }

9、js中call,apply,bind

百度JavaScript中call,apply,bind办法的总结。

10、Promise

一句话归纳Promise:Promise方针用于异步操作,它表明一个没有完结且估计在未来完结的异步操作。

promise是用来处理两个问题的:

  • 回调阴间,代码难以保护,常常第一个的函数的输出是第二个函数的输入这种现象
  • promise能够支撑多个并发的恳求,获取并发恳求中的数据

这个promise能够处理异步的问题,自身不能说promise是异步的

/*Promise 的简略完结*/
class MyPromise {
constructor(fn) {
this.resolvedCallbacks = [];
this.rejectedCallbacks = [];
this.state = "PADDING";
this.value = "";
fn(this.resolve.bind(this), this.reject.bind(this));
}
resolve(value) {
if (this.state === "PADDING") {
this.state = "RESOLVED";
this.value = value;
this.resolvedCallbacks.forEach(cb => cb());
}
}
reject(value) {
if (this.state === "PADDING") {
this.state = "REJECTED";
this.value = value;
this.rejectedCallbacks.forEach(cb => cb());
}
}
then(resolve = function() {}, reject = function() {}) {
if (this.state === "PADDING") {
this.resolvedCallbacks.push(resolve);
this.rejectedCallbacks.push(reject);
}
if (this.state === "RESOLVED") {
resolve(this.value);
}
if (this.state === "REJECTED") {
reject(this.value);
}
}
}

11、async/await

怎么运用 Async 函数

async function timeout(ms) {
await new Promise((resolve) => {
setTimeout(resolve, ms);
});
}
async function asyncPrint(value, ms) {
await timeout(ms);
console.log(value);
}
asyncPrint('hello world', 50);

上面代码指定50毫秒今后,输出hello world。进一步说,async函数完全能够看作多个异步操作,包装成的一个 Promise 方针,而await指令便是内部then指令的语法糖。

待弥补。。。

12、深仿制、浅仿制

浅仿制和深仿制都只针关于引证数据类型,浅仿制只仿制指向某个方针的指针,而不仿制方针自身,新旧方针仍是同享同一块内存;但深仿制会别的发明一个如出一辙的方针,新方针跟原方针不同享内存,修正新方针不会改到原方针;

差异:浅仿制只仿制方针的第一层特色、深仿制能够对方针的特色进行递归仿制;



浅仿制的完结办法

  1. 自界说函数
function simpleCopy (initalObj) {
var obj = {};
for ( var i in initalObj) {
obj[i] = initalObj[i];
}
return obj;
}
  1. ES6 的 Object.assign()
let newObj = Object.assign({}, obj);
  1. ES6 的方针扩展
let newObj = {...obj};

深仿制的完结办法

  1. JSON.stringify 和 JSON.parse


用 JSON.stringify 把方针转换成字符串,再用 JSON.parse 把字符串转换成新的方针。

let newObj = JSON.parse(JSON.stringify(obj));
  1. lodash


用 lodash 函数库供给的 _.cloneDeep 办法完结深仿制。

var _ = require('lodash');
var newObj = _.cloneDeep(obj);
  1. 自己封装
function deepClone(obj) {
let objClone = Array.isArray(obj) ? [] : {};
if (obj && typeof obj === "object") {
// for...in 会把承继的特色一同遍历
for (let key in obj) {
// 判别是不是自有特色,而不是承继特色
if (obj.hasOwnProperty(key)) {
//判别ojb子元素是否为方针或数组,假如是,递归仿制
if (obj[key] && typeof obj[key] === "object") {
objClone[key] = this.deepClone(obj[key]);
} else {
//假如不是,简略仿制
objClone[key] = obj[key];
}
}
}
}
return objClone;
}

13、跨域

跨域需求针对浏览器的同源战略来了解,同源战略指的是恳求有必要是同一个端口,同一个协议,同一个域名,不同源的客户端脚本在没有清晰授权的情况下,不能读写对方资源。

受浏览器同源战略的影响,不是同源的脚本不能操作其他源下面的方针。想要操作另一个源下的方针是就需求跨域。

  • jsonp
  • iframe
  • 跨域资源同享(CORS)
  • nginx 署理跨域

14、for in 和 for of

  • for in
1.一般用于遍历方针的可枚举特色。以及方针从结构函数原型中承继的特色。关于每个不同的特色,句子都会被履行。
2.不主张运用for in 遍历数组,由于输出的次序是不固定的。
3.假如迭代的方针的变量值是null或许undefined, for in不履行循环体,主张在运用for in循环之前,先查看该方针的值是不是null或许undefined
  • for of
1.for…of 句子在可迭代方针(包含 Array,Map,Set,String,TypedArray,arguments 方针等等)上创立一个迭代循环,调用自界说迭代钩子,并为每个不同特色的值履行句子

遍历方针

var s = {
a: 1,
b: 2,
c: 3
}
var s1 = Object.create(s);
for (var prop in s1) {
console.log(prop); //a b c
console.log(s1[prop]); //1 2 3
}
for (let prop of s1) {
console.log(prop); //报错如下 Uncaught TypeError: s1 is not iterable
}
for (let prop of Object.keys(s1)) {
console.log(prop); // a b c
console.log(s1[prop]); //1 2 3
}

15、怎么阻挠冒泡?

冒泡型工作:工作依照从最特定的工作方针到最不特定的工作方针(document方针)的次序触发。

w3c的办法是e.stopPropagation(),IE则是运用e.cancelBubble = true。

//阻挠冒泡行为
function stopBubble(e) {
//假如供给了工作方针,则这是一个非IE浏览器
if ( e && e.stopPropagation )
//因而它支撑W3C的stopPropagation()办法
e.stopPropagation();
else
//不然,咱们需求运用IE的办法来撤销工作冒泡
window.event.cancelBubble = true;
}

16、怎么阻挠默许工作?

w3c的办法是e.preventDefault(),IE则是运用e.returnValue = false

//阻挠浏览器的默许行为
function stopDefault( e ) {
//阻挠默许浏览器动作(W3C)
if ( e && e.preventDefault )
e.preventDefault();
//IE中阻挠函数器默许动作的办法
else
window.event.returnValue = false;
return false;
}

17、var,let,const

//变量提高
console.log(a); // undefined
console.log(b); // 报错
console.log(c); // 报错
var a = 1;
let b = 2;
const c = 3;
// 大局声明
console.log(window.a) // 1
// 重复声明
let b = 200;//报错

其实这儿很简略了解,var是能够变量提高的。而let和const是有必要声明后才干调用的。关于let和const来说,这儿便是暂缓性死区。



18、Class

es6新增的Class其实也是语法糖,js底层其实没有class的概念的,其实也是原型承继的封装。

class People {
constructor(props) {
this.props = props;
this.name = '汪某';
}
callMyName() {
console.log(this.name);
}
}
class Name extends People { // extends 其实便是承继了哪个类
constructor(props) {
// super相当于 把类的原型拿过来
// People.call(this, props)
super(props)
}
callMyApple() {
console.log('我是汪某!')
}
}
let a = new Name('啊啊啊')
a.callMyName(); //汪某
a.callMyApple(); // 我是汪某!

19、Set

Set数据结构相似数组,但一切成员的值仅有。

let a = new Set();
[1,2,2,1,3,4,5,4,5].forEach(x=>a.add(x));
for(let k of a){
console.log(k)
};
// 1 2 3 4 5

根本运用

let a = new Set([1,2,3,3,4]);
[...a]; // [1,2,3,4]
a.size; // 4
// 数组去重
[...new Set([1,2,3,4,4,4])];// [1,2,3,4]

办法

  • add(value):增加某个值,回来 Set 结构自身。
  • delete(value):删去某个值,回来一个布尔值,表明删去是否成功。
  • has(value):回来一个布尔值,表明该值是否为Set的成员。
  • clear():铲除一切成员,没有回来值。
let a = new Set();
a.add(1).add(2); // a => Set(2) {1, 2}
a.has(2); // true
a.has(3); // false
a.delete(2); // true a => Set(1) {1}
a.clear(); // a => Set(0) {}

20、Map

Map结构供给了“值—值”的对应,是一种更完善的 Hash 结构完结。

let a = new Map();
let b = {name: 'leo' };
a.set(b,'my name'); // 增加值
a.get(b); // 获取值
a.size; // 获取总数
a.has(b); // 查询是否存在
a.delete(b); // 删去一个值
a.clear(); // 清空一切成员 无回来

根本运用

  • 传入数组作为参数,指定键值对的数组。
let a = new Map([
['name','wzx'],
['age',23]
])
  • 假如对同一个键屡次赋值,后边的值将掩盖前面的值。
let a = new Map();
a.set(1,'aaa').set(1,'bbb');
a.get(1); // 'bbb'
  • 假如读取一个不知道的键,则回来undefined。
new Map().get('asdsad'); // undefined
  • 相同的值的两个实例,在 Map 结构中被视为两个键。
let a = new Map();
let a1 = ['aaa'];
let a2 = ['aaa'];
a.set(a1,111).set(a2,222);
a.get(a1); // 111
a.get(a2); // 222

办法

  • keys():回来键名的遍历器。
  • values():回来键值的遍历器。
  • entries():回来一切成员的遍历器。
  • forEach():遍历 Map 的一切成员。
let a = new Map([
['name', 'leo'],
['age', 18]
])
for (let i of a.keys()) {
console.log(i)
};
//name
//age
for (let i of a.values()) {
console.log(i)
};
//leo
//18
for (let i of a.entries()) {
console.log(i)
};
//["name", "leo"]
a.forEach((v, k, m) => {
console.log(`key:${k},value:${v},map:${m}`)
})
//["age", 18]

三、手撸代码

1、完结一个new操作符

function New(func) {
var res = {};
if (func.prototype !== null) {
res.__proto__ = func.prototype;
}
var ret = func.apply(res, Array.prototype.slice.call(arguments, 1));
if ((typeof ret === "object" || typeof ret === "function") && ret !== null) {
return;
ret;
}
return;
res;
}
var obj = New(A, 1, 2);
// equals to
var obj = new A(1, 2);

2、完结一个call或 apply

  • call
Function.prototype.call2 = function (context) {
var context = context || window;
context.fn = this;
var args = [];
for(var i = 1, len = arguments.length; i < len; i++) {
args.push('arguments[' + i + ']');
}
var result = eval('context.fn(' + args +')');
delete context.fn
return result;
}
  • apply
Function.prototype.apply2 = function (context, arr) {
var context = Object(context) || window;
context.fn = this;
var result;
if (!arr) {
result = context.fn();
}
else {
var args = [];
for (var i = 0, len = arr.length; i < len; i++) {
args.push('arr[' + i + ']');
}
result = eval('context.fn(' + args + ')')
}
delete context.fn
return result;
}

参考文献:JavaScript深化之call和apply的模仿完结

3、完结一个Function.bind

Function.prototype.bind2 = function (context) {
if (typeof this !== "function") {
throw new Error("Function.prototype.bind - what is trying to be bound is not callable");
}
var self = this;
var args = Array.prototype.slice.call(arguments, 1);
var fNOP = function () {};
var fbound = function () {
self.apply(this instanceof self ? this : context, args.concat(Array.prototype.slice.call(arguments)));
}
fNOP.prototype = this.prototype;
fbound.prototype = new fNOP();
return fbound;
}

参考文献:JavaScript深化之bind的模仿完结

4、完结一个承继

function Parent(name) {
this.name = name;
}
Parent.prototype.sayName = function() {
console.log('parent name:', this.name);
}
function Child(name, parentName) {
Parent.call(this, parentName);
this.name = name;
}
function create(proto) {
function F() {}
F.prototype = proto;
return new F();
}
Child.prototype = create(Parent.prototype);
Child.prototype.sayName = function() {
console.log('child name:', this.name);
}
Child.prototype.constructor = Child;
var parent = new Parent('汪某');
parent.sayName();// parent name: 汪某
var child = new Child('son', '汪某');

5、手写一个Promise(中高档必考)

面试够用版

function myPromise(constructor) {
let self = this;
self.status = "pending"
//界说状况改动前的初始状况
self.value = undefined;
//界说状况为resolved的时分的状况
self.reason = undefined;
//界说状况为rejected的时分的状况
function resolve(value) {
//两个==="pending",确保了状况的改动是不可逆的
if (self.status === "pending") {
self.value = value;
self.status = "resolved";
}
}
function reject(reason) {
//两个==="pending",确保了状况的改动是不可逆的
if (self.status === "pending") {
self.reason = reason;
self.status = "rejected";
}
}
//捕获结构反常
try {
constructor(resolve, reject);
} catch (e) {
reject(e);
}
}
//一同,需求在 myPromise的原型上界说链式调用的 then办法:
myPromise.prototype.then = function(onFullfilled, onRejected) {
let self = this;
switch (self.status) {
case "resolved":
onFullfilled(self.value);
break;
case "rejected":
onRejected(self.reason);
break;
default:
}
}
//测验一下:
var p = new myPromise(function(resolve, reject) {
resolve(1)
});
p.then(function(x) {
console.log(x)
})

高档版请参考文献:史上最最最具体的手写Promise教程

6、手写防抖(Debouncing)和节省(Throttling)

完整版详见上方,此处给出面试版

// 防抖函数
function debounce(fn, wait = 50, immediate) {
let timer;
return function() {
if (immediate) {
fn.apply(this, arguments)
}
if (timer) clearTimeout(timer)
timer = setTimeout(() => {
fn.apply(this, arguments)
}, wait)
}
// 节省函数
function throttle(fn, wait) {
let prev = new Date();
return function() {
const args = arguments;
const now = new Date();
if (now - prev > wait) {
fn.apply(this, args);
prev = new Date();
}
}
}

7、手写一个JS深仿制

面试版

function deepCopy(obj) {
//判别是否是简略数据类型,
if (typeof obj == "object") {
//杂乱数据类型
var result = obj.constructor == Array ? [] : {};
for (let i in obj) {
result[i] = typeof obj[i] == "object" ? deepCopy(obj[i]) : obj[i];
}
} else {
//简略数据类型 直接 == 赋值
var result = obj;
}
return result;
}

四、VUE

1、Vue的双向数据绑定原理是什么?

vue.js 是选用数据绑架结合发布者-订阅者办法的办法,经过Object.defineProperty()来绑架各个特色的setter,getter,在数据改动时发布音讯给订阅者,触发相应的监听回调。

//vue完结数据双向绑定的原理便是用Object.defineproperty()从头界说(set办法)方针设置特色值和(get办法)获取特色值的操作来完结的。
//Object.property()办法的解说:Object.property(参数1,参数2,参数3) 回来值为该方针obj
//其间参数1为该方针(obj),参数2为要界说或修正的方针的特色名,参数3为特色描述符,特色描述符是一个方针,主要有两种办法:数据描述符和存取描述符。这两种方针只能挑选一种运用,不能混合运用。而get和set归于存取描述符方针的特色。
//这个办法会直接在一个方针上界说一个新特色或许修正方针上的现有特色,并回来该方针。












var model = {
message: ""
};
var models = myapp.querySelectorAll("[v-model=message]");
for (var i = 0; i < models.length; i++) {
models[i].onkeyup = function() {
model[this.getAttribute("v-model")] = this.value;
}
}
// 观察者办法 / 钩子函数
// defineProperty 来界说一个方针的某个特色
Object.defineProperty(model, "message", {
set: function(newValue) {
var binds = myapp.querySelectorAll("[v-bind=message]");
for (var i = 0; i < binds.length; i++) {
binds[i].innerHTML = newValue;
};
var models = myapp.querySelectorAll("[v-model=message]");
for (var i = 0; i < models.length; i++) {
models[i].value = newValue;
};
this.value = newValue;
},
get: function() {
return this.value;
}
})




2、请具体说下你对vue生命周期的了解?

一共分为8个阶段创立前/后,载入前/后,更新前/后,毁掉前/后

  • beforeCreate 创立前履行(vue实例的挂载元素$el和数据方针data都为undefined,还未初始化)
  • created 完结创立 (完结了data数据初始化,el还未初始化)
  • beforeMount 载入前(vue实例的$el和data都初始化了,但仍是挂载之前为虚拟的dom节点,data.message还未替换。)
  • mounted 载入后html现已烘托(vue实例挂载完结,data.message成功烘托。)
  • beforeUpdate 更新前状况(view层的数据改动前,不是data中的数据改动前)
  • updated 更新状况后
  • beforeDestroy 毁掉前
  • destroyed 毁掉后 (在履行destroy办法后,对data的改动不会再触发周期函数,阐明此刻vue实例现已免除了工作监听以及和dom的绑定,可是dom结构仍然存在)

说一下每一个阶段能够做的工作

  • beforeCreate:能够在这儿加一个loading工作,在加载实例时触发。
  • created:初始化完结时的工作写这儿,假如这儿完毕了loading工作,异步恳求也在这儿调用。
  • mounted:挂在元素,获取到DOM节点
  • updated:对数据进行处理的函数写这儿。
  • beforeDestroy:能够写一个承认中止工作的承认框。

附上一张中文解析图




3、动态路由界说和获取

在 router 目录下的 index.js 文件中,对 path 特色加上 /:id。

运用 router 方针的 params.id 获取

4、vue-router 有哪几种导航钩子?

三种

  1. 大局导航钩子(跳转前进行判别阻拦)
  • router.beforeEach(to, from, next),
  • router.beforeResolve(to, from, next),
  • router.afterEach(to, from ,next)
  1. 组件内钩子
  • beforeRouteEnter
  • beforeRouteUpdate
  • beforeRouteLeave
  1. 独自路由独享组件
  • beforeEnter

5、组件之间的传值通讯?

  • 父组件向子组件传值:
  • 子组件在props中创立一个特色,用来接纳父组件传过来的值;
  • 在父组件中注册子组件;
  • 在子组件标签中增加子组件props中创立的特色;
  • 把需求传给子组件的值赋给该特色
  • 子组件向父组件传值:
  • 子组件中需求以某种办法(如点击工作)的办法来触发一个自界说的工作;
  • 将需求传的值作为$emit的第二个参数,该值将作为实参传给呼应工作的办法;
  • 在父组件中注册子组件并在子组件标签上绑定自界说工作的监听。

6、vuex

是一个能便利vue实例及其组件传输数据的插件 便利传输数据,作为公共存储数据的一个库

state: 状况中心mutations: 更改状况,同步的actions: 异步更改状况getters: 获取状况modules: 将state分红多个modules,便于管理

运用场景:单页运用中,组件之间的状况。音乐播映、登录状况、参加购物车。

网上找的一个通俗易懂的了解vuex的比如

公司有个库房1.State(公司的库房)2.Getter(只能取出物品,包装一下,不能改动物品任何特色)3.Muitation(库房管理员,只需他能够直接存储到库房)4.Action(公司的物料采购员,担任从外面买东西和接货, 要往库房存东西,告知库房管理员要存什么)十分要注意的当地:只需改写或许退出浏览器,库房清空。作者:A Loity原文:https://juejin.im/post/5cb92d9a5188254160581b87#heading-35