网易面试官:请你实现一下JS重载?可不是TS重载哦!

前言

大家好,我是林三心,用最通俗易懂的话讲最难的知识点是我的座右铭,基础是进阶的前提是我的初心。今天给大家讲一道题,是一道网易的面试题

  • 一位同学:“如何实现JS重载?”
  • 我:“JS有重载吗?不是TS才有吗?”
  • 一位同学:“有的,这是网易一道面试题”
  • 我:“好吧我想想哈!”
image.png

什么是重载

我第一次看到重载这个词还是在以前学习Java的时候,我一直觉得JavaScript是没有重载的,直到TypeScript的出现,所以我一直觉得JavaScript没有重载,TypeScript才有,但是现在看来我是错的。

我理解的重载是:同样的函数,不同样的参数个数,执行不同的代码,比如:

/*
* 重载
*/

function fn(name{
  console.log(`我是${name}`)
}

function fn(name, age{
  console.log(`我是${name},今年${age}岁`)
}

function fn(name, age, sport{
  console.log(`我是${name},今年${age}岁,喜欢运动是${sport}`)
}

/*
* 理想结果
*/

fn('林三心'// 我是林三心
fn('林三心'18// 我是林三心,今年18岁
fn('林三心'18'打篮球'// 我是林三心,今年18岁,喜欢运动是打篮球

但是直接在JavaScript中这么写,肯定是不行的,咱们来看看上面代码的实际执行结果,可以看到,最后一个fn的定义,把前面两个都给覆盖了,所以没有实现重载的效果

我是林三心,今年undefined岁,喜欢运动是undefined
我是林三心,今年18岁,喜欢运动是undefined
我是林三心,今年18岁,喜欢运动是打篮球

我的做法

其实,想要实现理想的重载效果,我还是有办法的,我可以只写一个fn函数,并在这个函数中判断arguments类数组的长度,执行不同的代码,就可以完成重载的效果

function fn({
  switch (arguments.length) {
    case 1:
      var [name] = arguments
      console.log(`我是${name}`)
      break;
    case 2:
      var [name, age] = arguments
      console.log(`我是${name},今年${age}岁`)
      break;
    case 3:
      var [name, age, sport] = arguments
      console.log(`我是${name},今年${age}岁,喜欢运动是${sport}`)
      break;
  }
}

/*
* 实现效果
*/

fn('林三心'// 我是林三心
fn('林三心'18// 我是林三心,今年18岁
fn('林三心'18'打篮球'// 我是林三心,今年18岁,喜欢运动是打篮球

但是那位同学说,网易的面试官好像觉得这么实现可以是可以,但是还有没有更好的实现方法,我就懵逼了。

高端做法

image.png

经过了我的一通网上查找资料,发现了一种比较高端的做法,可以利用闭包来实现重载的效果。这个方法在JQuery之父John Resig写的《secrets of the JavaScript ninja》中,这种方法充分的利用了闭包的特性!

function addMethod(object, name, fn{
  var old = object[name]; //把前一次添加的方法存在一个临时变量old里面
  object[name] = function (// 重写了object[name]的方法
    // 如果调用object[name]方法时,传入的参数个数跟预期的一致,则直接调用
    if (fn.length === arguments.length) {
      return fn.apply(thisarguments);
      // 否则,判断old是否是函数,如果是,就调用old
    } else if (typeof old === "function") {
      return old.apply(thisarguments);
    }
  }
}

addMethod(window'fn', (name) => console.log(`我是${name}`))
addMethod(window'fn', (name, age) => console.log(`我是${name},今年${age}岁`))
addMethod(window'fn', (name, age, sport) => console.log(`我是${name},今年${age}岁,喜欢运动是${sport}`))

/*
* 实现效果
*/


window.fn('林三心'// 我是林三心
window.fn('林三心'18// 我是林三心,今年18岁
window.fn('林三心'18'打篮球'// 我是林三心,今年18岁,喜欢运动是打篮球

参考资料

  • 浅谈JavaScript函数重载

结语

如果你觉得此文对你有一丁点帮助,点个赞,鼓励一下林三心哈哈。或者加入我的群哈哈,咱们一起摸鱼一起学习 : meron857287645


相关推荐

  • 分享15个高级前端开发小技巧
  • 从Java到json:探索 Jackson 的魔力
  • 2.3k star,一整套完整的 AI 助手系统开源了,逼格拉满、开箱即用,支持一键部署
  • 【福利】知识图谱实践资料最后2天免费赠送!
  • 张俊林:揭去神秘面纱,Sora关键技术逆向工程图解
  • 答应我,在vue中不要滥用watch好吗?
  • 目前工资最高的几家外包公司汇总!(2024最新版)
  • 畅销10W册的《码农翻身》出第二部啦
  • 万字:深度解析“外卡收单”体系
  • 腾讯文档收集表后台重构:改造一个巨石单体!
  • 告别 BeanUtil.copyProperties,这款IDEA插件才是最优的替代方案!
  • 真是太凡尔赛了!一位女硕士研究生被省烟草局提前录取了,但却高兴不起来,自己学的是计算机,华为也发了offer。。。
  • Java 22 正式发布,一文了解全部新特性
  • JDK22 正式发布了 !
  • 推荐一款超高颜值的开源服务器仪表盘,非常不错!
  • 大模型提示学习样本量有玄机,自适应调节方法好
  • 大模型增量预训练新技巧-解决灾难性遗忘
  • ChatGPT参数规模被扒:只有7B
  • Kaggle知识点:sktime时序建模库
  • [开源]前后端分离的企业级内容管理系统,站群管理、多平台静态化