IT学习网是免费的终身在线学习平台,现在主要提供IT(互联网)方面的教程,博客等方面的内容
主页 > 前端 > > 正文

儿童编程学习前端开发岗位面试中常考的源代码实现

来源:IT学习网整理 发布时间:2020-02-14 18:55 标签:开发前端岗位实现源代码中常面试
浏览:
手动撸个call/apply/bind,实现call来看下call的原生表现形式:如果一个函数作为一个对象的属性,那么通过对象的.运算符调用此函数,this就是此对象;apply和call实现类似,只是传入的参数形式是数组形式"/>前端开发岗位面试中常考的源代码实现

前端开发前端导航工具/手册更多栏目

折扣返利

网站投稿

书籍/周边

站内搜索

fly63前端网

提交

我要投稿

前端开发岗位面试中常考的源代码实现

时间: 2019-08-08阅读: 166标签: 面试

手动撸个call/apply/bind实现call

来看下call的原生表现形式:

function test(arg1, arg2) { console.log(arg1, arg2) console.log(this.a, this.b) } run.call({ a: 'a', b: 'b' }, 1, 2)

好了,开始手动实现我们的call2。在实现的过程有个关键:

如果一个函数作为一个对象的属性,那么通过对象的.运算符调用此函数,this就是此对象

let obj = { a: 'a', b: 'b', test: function (arg1, arg2) { console.log(arg1, arg2) // this.a 就是 a; this.b 就是 b console.log(this.a, this.b) } } obj.test(1, 2)

知道了实现关键,下面就是我们模拟的call:

Function.prototype.call2 = function(context) { if(typeof this !== 'function') { throw new TypeError('Error') } // 默认上下文是window context = context || window // 保存默认的fn const { fn } = context // 前面讲的关键,将函数本身作为对象context的属性调用,自动绑定this context.fn = this const args = [...arguments].slice(1) const result = context.fn(...args) // 恢复默认的fn context.fn = fn return result } // 以下是测试代码 function test(arg1, arg2) { console.log(arg1, arg2) console.log(this.a, this.b) } test.call2({ a: 'a', b: 'b' }, 1, 2) 实现apply

apply和call实现类似,只是传入的参数形式是数组形式,而不是逗号分隔的参数序列。

因此,借助es6提供的...运算符,就可以很方便的实现数组和参数序列的转化。

Function.prototype.apply2 = function(context) { if(typeof this !== 'function') { throw new TypeError('Error') } context = context || window const { fn } = context context.fn = this let result if(Array.isArray(arguments[1])) { // 通过...运算符将数组转换为用逗号分隔的参数序列 result = context.fn(...arguments[1]) } else { result = context.fn() } context.fn = fn return result } /** * 以下是测试代码 */ function test(arg1, arg2) { console.log(arg1, arg2) console.log(this.a, this.b) } test.apply2({ a: 'a', b: 'b' }, [1, 2]) 实现bind

bind的实现有点意思,它有两个特点:

本身返回一个新的函数,所以要考虑new的情况

可以“保留”参数,内部实现了参数的拼接

Function.prototype.bind2 = function(context) { if(typeof this !== 'function') { throw new TypeError('Error') } const that = this // 保留之前的参数,为了下面的参数拼接 const args = [...arguments].slice(1) return function F() { // 如果被new创建实例,不会被改变上下文! if(this instanceof F) { return new that(...args, ...arguments) } // args.concat(...arguments): 拼接之前和现在的参数 // 注意:arguments是个类Array的Object, 用解构运算符..., 直接拿值拼接 return that.apply(context, args.concat(...arguments)) } } /** * 以下是测试代码 */ function test(arg1, arg2) { console.log(arg1, arg2) console.log(this.a, this.b) } const test2 = test.bind2({ a: 'a', b: 'b' }, 1) // 参数 1 test2(2) // 参数 2 实现深拷贝函数

实现一个对象的深拷贝函数,需要考虑对象的元素类型以及对应的解决方案:

基础类型:这种最简单,直接赋值即可

对象类型:递归调用拷贝函数

数组类型:这种最难,因为数组中的元素可能是基础类型、对象还可能数组,因此要专门做一个函数来处理数组的深拷贝

/** * 数组的深拷贝函数 * @param {Array} src * @param {Array} target */ function cloneArr(src, target) { for(let item of src) { if(Array.isArray(item)) { target.push(cloneArr(item, [])) } else if (typeof item === 'object') { target.push(deepClone(item, {})) } else { target.push(item) } } return target } /** * 对象的深拷贝实现 * @param {Object} src * @param {Object} target * @return {Object} */ function deepClone(src, target) { const keys = Reflect.ownKeys(src) let value = null for(let key of keys) { value = src[key] if(Array.isArray(value)) { target[key] = cloneArr(value, []) } else if (typeof value === 'object') { // 如果是对象而且不是数组, 那么递归调用深拷贝 target[key] = deepClone(value, {}) } else { target[key] = value } } return target }

热门文章

  • 用VPN得小心了,一程序员非法出售 VPN 被判
    用VPN得小心了,一程序员非法出售 VPN 被判

    用VPN得小心了,一程序员非法出售 VPN 被判

    上海市宝山区人民法院审理了一起案件,被告人戴某原在某证券管理公司从事软件开发工作。自 2016 年 4 月起,其为牟取非法利益,创建某网站,并在网站...

  • h5通过css实现禁止ios端长按复制选中文字
    h5通过css实现禁止ios端长按复制选中文字

    h5通过css实现禁止ios端长按复制选中文字

    在ios端默认的长按选择,可以对文字进行复制粘贴。但是在实际开发中,针对一些按钮一般要避免长按时弹出选中文字,或者一些罩层要避免弹出。 这篇文...

  • 自学教程腾讯开源新生移动跨端开发框架
    自学教程腾讯开源新生移动跨端开发框架

    自学教程腾讯开源新生移动跨端开发框架

    自学教程原标题:腾讯开源新生移动跨端开发框架Hippy:支持iOS、安卓 来源:IT之家 新酷产品第一时间免费试玩,还有众多优质达人分享独到生活经验,快...

  • it技术是什么玉米2005(C2005)11月12日行情及
    
it技术是什么玉米2005(C2005)11月12日行情及

    it技术是什么玉米2005(C2005)11月12日行情及

    (玉米2005)主力合约(C2005)今日开盘价为1937.0000元,收盘价为1919.0000元,较上一个交易日下跌-20.0000元 ,涨/跌幅度...

  • 编程视频教程vue里的$refs属性
    编程视频教程vue里的$refs属性

    编程视频教程vue里的$refs属性

    编程视频教程vuejs的极大程度的帮助减少了对dom的操作,他主要通过添加ref属性,但是当获取this.$refs属性时,稍有不注意就会输出undefined导致我们对dom节点...

后端

更多 >
后端 新手学网站编程入门将促进境内市场与国
后端 学编程学习SpatialOS作为英礴旗下的下一代
后端 编程基础怎么学看一看其他和这家公司合
后端 编程自学多长时间若申请将手中持有的基
后端 编程需要学习那些如何教三岁宝宝学数学

工具资源

更多 >