原生JS常见问题

1.原型对象/ 构造函数/实例

  • 原型对象:构造函数prototype属性指向的对象
  • 构造函数:创建对象的一种方式
  • 实例:构造函数创建的一个对象(new一下)
  • constructor: 一个属性,对象独有,指向构造函数
  • proto: 一个隐式属性,函数和对象都有这个属性
  • prototype:一个属性仅函数独有,指向该函数的原型对象、
    prototype属性可以给函数共享(继承)方法、属性,而_proto_是查找某函数或对象的原型链方式

2. 原型链

属性查找: 从实例本身一层层向上查找,直到访问到对象的原型。
属性修改:只会修改实例本身的属性,如果不存在,则添加该属性。如果需要修改原型的属性时,可以使用例如Vue.prototype.xxx = xxx;但是这样会造成所有Vue的实例属性会发生改变。

3. 闭包

函数外部访问函数内部的方法;闭包其实就是一个函数,这个函数能够访问其他函数的作用域中的变量。
在js中,如果一个对象不再被引用,这个对象会被GC回收,否则会被一直保存在内存中。
《JavaScript高级编程》书中建议:由于闭包会携带包含它的函数的作用域,因为会比其他函数占用更多内容,过度使用闭包,会导致内存占用过多。

4. 对象的拷贝

  • 浅拷贝:以赋值的形式拷贝引用对象,指向同一个地址,修改时原对象也会受到影响(寻址操作,例如访问数据类型是数组),常用Object.assign, 展开运算符(...).
  • 深拷贝: 完全拷贝一个新对象,修改时原对象不受任何影响(寻值操作:例如访问数据类型为字符串),常用 JSON.parse(JSON.stringify(obj)), 递归进行逐一赋值

5. new运算符的执行过程

  • 新生成一个对象
  • 链接到原型; obj.proto = constructor.prototype
  • 绑定this: apply
  • 返回新对象(如果构造器有自己的return时,则返回该值)

6. instanceof 原理

objA instanceof objB: objA的原型链上能否找到objB的原型
instanceof 跟 typeof区别:typeof 返回该参数数据类型,返回的是string;instanceof 判断参数是否存在继承关系,返回时Boolean

7. 模块化

通用的js模块规范主要有:CommonJS 、AMD 、ES6

  • CommonJS : require/module.exports/exports
  • AMD: require/defined
  • ES6: import / export
require 跟import的区别
  • require 是AMD引入的规范,import是ES6的规范
  • import是编译时调用只能放在文件开头,require 是运行时调用,理论上是可以运行在代码任何地方
  • require 是值拷贝过程,导出值改变不会影响导入值,require的结果就是obj、number、string、fun,再把结果赋值给一个变量
  • import是解构赋值的过程,指向内存地址,导入值会随着导出值变化,但是目前所有的引擎还没有实现import,所以使用babel+ES6, ES6转码成ES5在执行,import最终会被转码成require

8. 函数节流、函数防抖

  • 函数节流是指一定时间内js方法只跑一次。比如人的眨眼睛,就是一定时间内眨一次。这是函数节流最形象的解释。函数节流应用的实际场景,多数在监听页面元素滚动事件的时候会用到。因为滚动事件,是一个高频触发的事件
函数节流的要点是,声明一个变量当标志位,记录当前代码是否在执行。 如果空闲,则可以正常触发方法执行。如果代码正在执行,则取消这次方法执行,直接return。
let canRun = true;
document.getElementById("body").onscroll = function(){
    if (!canRun) {
        // 判断是否已空闲,如果在执行中,则直接return
        return;
    }
    canRun = false;
    setTimeout(function(){
        console.log("函数节流");
        canRun = true;
    }, 300);
}
  • 函数防抖
    函数防抖的应用场景,最常见的就是用户注册时候的手机号码验证和邮箱验证了。只有等用户输入完毕后,前端才需要检查格式是否正确,如果不正确,再弹出提示语
函数防抖的要点,也是需要一个setTimeout来辅助实现。延迟执行需要跑的代码。
如果方法多次触发,则把上次记录的延迟执行代码用clearTimeout清掉,重新开始。
如果计时完毕,没有方法进来访问触发,则执行代码
let timer = false;
document.getElementById("debounce").onInput = function(){
    clearTimeout(timer); // 清除未执行的代码,重置回初始化状态
    timer = setTimeout(function(){
        console.log("函数防抖");
    }, 300);
};

两者的区别: 节流是每隔一段时间执行一次,防抖只执行一次

9. this

  • 普通对象:this指向器所在函数对象,谁调用函数指向谁
  • 构造函数: this指向被创建的新对象的实例对象
  • DOM事件: this指向触发事件的DOM元素
  • call()和apply():this指向第一个参数对象
  • setTimeout和setInterval: this 指向全局
  • 箭头函数: this 指向最初定义函数时的作用域
var  b = 11
var obj = {
        b:22,
        say: () => {
            console.log(this.b)
        }
 }
 obj.say() // 输出11

改变this的方式

  • call: fn.call(target, 1, 2)
  • apply: fn.call(target, [1, 2])
  • bind: fn.bind(target)(1, 2)
    apply 和 call 的用法几乎相同, 是为了借用别的对象的方法. 唯一的差别在于:当函数需要传递多个变量时, apply 可以接受一个数组作为参数输入, call 则是接受一系列的单独变量 .

和call很相似,第一个参数是this的指向,从第二个参数开始是接收的参数列表。区别在于bind方法返回值是函数以及bind接收的参数列表的使用。bind 方法不会立即执行,而是返回一个改变了上下文 this 后的函数。而原函数 printName 中的 this 并没有被改变,依旧指向全局对象 window。

 var obj = {
        message: 'My name is: '
    }
  function getName(firstName, lastName) {
        console.log(this.message + firstName + ' ' + lastName)
    }
 getName.call(obj, 'zhang', 'xiao')         输出 My name is: zhang xiao;
 getName.apply(obj, ['zhang', 'xiao'])   输出 My name is: zhang xiao;
let fn =  getName.bind(obj)
    console.log(fn)
    // 输出 getName(firstName, lastName) {
    //     console.log(this.message + firstName + ' ' + lastName)
    // }
    fn('zhang', 'xiao') // 输出  My name is: zhang xiao

10.数组

map 、forEach相同点

  • 都是循环遍历数组中的每一项,支持三个参数,item, index, arr
  • 匿名函数this指向window
  • 只能遍历数组,而且都不会改变原数组

map 、forEach区别

map返回的是一个新数组,数组中的元素为处理之后的值。arr为空时,map返回的也是空数组,forEach对于空数组是不会调用回调函数的,物理arr是否为空,forEach返回的都是underfine. 这个方法只是将数组中的每一项作为callback执行一次。

11. ES6

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 199,440评论 5 467
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 83,814评论 2 376
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 146,427评论 0 330
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 53,710评论 1 270
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 62,625评论 5 359
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,014评论 1 275
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,511评论 3 390
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,162评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,311评论 1 294
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,262评论 2 317
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,278评论 1 328
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,989评论 3 316
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,583评论 3 303
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,664评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,904评论 1 255
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,274评论 2 345
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 41,856评论 2 339