前端进阶之旅前端进阶之旅
基础篇
进阶篇
高频篇
精选篇
手写篇
面经篇
AI 篇
原理篇
每日一题
小程序题库
知识卡片
  • 场景篇按分类整理的大前端场景考点
  • 历年面经按年份追踪真实考点
  • 算法题库NEW在线编码即时判题
  • 专项自测100 题快速查漏
  • 前端基础
    • HTTP从报文一路讲到 HTTPS
    • 浏览器渲染、事件循环、进程
    • 计算机基础Linux、网络、操作系统
  • 进阶专项
    • 设计模式23 种模式怎么用
    • 前端系统进阶学习大型项目工程化
    • 前端综合文章长期沉淀的实践文
  • 工程与工具
    • Node学习指南从环境搭建到服务端
    • NPM工作流script、依赖与发布
    • Docker容器化部署上手
    • Canvas图形与动画实战
  • 路线与导图
    • 思维导图知识点全景图
    • 学习路线按图索骥不跑偏
  • 动态
    • 公众号动态公众号历史文章
    • 博客动态站长的技术博客
    • 开发者导航常用工具与文档站
  • AI 助手随时提问,即时解析
  • AI 模拟面试模拟真实面试 + 报告
  • AI 知识地图串起全站知识点
  • AI 定制路线按你的简历现排
AI 热点
旧版
基础篇
进阶篇
高频篇
精选篇
手写篇
面经篇
AI 篇
原理篇
每日一题
小程序题库
知识卡片
  • 场景篇按分类整理的大前端场景考点
  • 历年面经按年份追踪真实考点
  • 算法题库NEW在线编码即时判题
  • 专项自测100 题快速查漏
  • 前端基础
    • HTTP从报文一路讲到 HTTPS
    • 浏览器渲染、事件循环、进程
    • 计算机基础Linux、网络、操作系统
  • 进阶专项
    • 设计模式23 种模式怎么用
    • 前端系统进阶学习大型项目工程化
    • 前端综合文章长期沉淀的实践文
  • 工程与工具
    • Node学习指南从环境搭建到服务端
    • NPM工作流script、依赖与发布
    • Docker容器化部署上手
    • Canvas图形与动画实战
  • 路线与导图
    • 思维导图知识点全景图
    • 学习路线按图索骥不跑偏
  • 动态
    • 公众号动态公众号历史文章
    • 博客动态站长的技术博客
    • 开发者导航常用工具与文档站
  • AI 助手随时提问,即时解析
  • AI 模拟面试模拟真实面试 + 报告
  • AI 知识地图串起全站知识点
  • AI 定制路线按你的简历现排
AI 热点
旧版
首页程序员面试题库函数 prototype 属性 箭头函数为何没有
JavaScript函数与作用域

所有函数都有 prototype 吗?箭头函数为什么没有?

不是。prototype 是给 new 用的:new 出来的实例会以它为原型。普通函数和 class 能被 new,所以有 prototype;箭头函数、async 函数、对象简写方法生来就不能 new,也就没有 prototype。

前端进阶之旅 · 一题精讲更新于 2026.09.29
JavaScript#函数与作用域#异步编程
先看核心答案读代码示例
理解线索

有没有 prototype 和能不能 new

  1. 普通函数和 class有 prototype,能 new,实例的原型就是它
  2. 箭头、async、简写方法没有 prototype,new 会抛 TypeError
  3. 生成器和异步生成器有 prototype,给生成器对象当原型,但不能 new

bind 返回的函数没有 prototype,但如果原函数能 new,绑定后的函数也能 new,实例的原型用的是原函数的 prototype。

核心回答

先记住这个答案

不是所有函数都有 prototype。这个属性只为 new 服务:new Foo() 创建的实例,原型会指向 Foo.prototype。普通函数声明、普通函数表达式和 class 能被 new,所以有 prototype。箭头函数、async 函数、对象和类里的简写方法,设计上就不能 new,所以没有 prototype。箭头函数之所以不能 new,是因为它没有自己的 this,而构造的核心就是把新对象作为 this 去初始化。

  • prototype 的用途是给 new 出来的实例当原型
  • 箭头函数、async 函数、简写方法没有 prototype,也不能 new
  • 生成器有 prototype,但照样不能 new
  • 判断能否 new 不能看有没有 prototype

把几类函数放在一起对比

光说结论容易记混,直接打印出来最清楚。

看 prototype 和 new 的结果JavaScript
function Normal() {}
const arrow = () => {}
async function asyncFn() {}
const obj = { method() {} }
function* gen() {}

console.log(typeof Normal.prototype) // 有
console.log(arrow.prototype, asyncFn.prototype, obj.method.prototype) // 都没有
console.log(typeof gen.prototype) // 生成器也有

for (const fn of [arrow, gen]) {
  try { new fn() } catch (e) { console.log(e.name) }
}
查看输出与解释
object
undefined undefined undefined
object
TypeError
TypeError

箭头函数、async 函数、简写方法的 prototype 都是 undefined,new 它们会直接报 TypeError: xxx is not a constructor。 生成器是个例外:gen.prototype 存在,但 new gen() 一样报错。它的 prototype 不是给 new 用的,而是给调用 gen() 返回的生成器对象当原型,Object.getPrototypeOf(gen()) === gen.prototype 为 true。async function* 异步生成器也是一样,有 prototype、不能 new。

为什么这些函数被设计成不能 new

new 做的事情是:创建一个空对象,把它的原型设为 Foo.prototype,再以它为 this 执行函数体。一个函数要能被 new,至少要有自己的 this,还要有意义地「初始化一个实例」。

箭头函数
箭头函数的 this 来自外层作用域,调用时不会创建自己的 this,没法把新对象绑定进去,所以不能 new,也就不需要 prototype。它被设计出来就是做轻量回调的。
async 函数和简写方法
async 函数一定返回 Promise,而 new 应该返回实例对象,两者冲突。简写方法 method() {} 是 ES6 明确规定的方法语义,它是用来被对象调用的行为,不是构造器。而 method: function () {} 这种写法到现在也能被 new,这是普通函数带来的能力,简写方法没有继承它。
回答前,多想一步

容易答错的地方

用 fn.prototype 判断函数能不能 new
生成器有 prototype 却不能 new,bind 返回的函数没有 prototype 却可能能 new,两头都会判断错。真要判断,只能 try { Reflect.construct(String, [], fn) } 这种方式试一下,或者在设计 API 时直接约定传入的是构造器还是普通函数。
以为 class 里的方法也有 prototype
class 本身有 prototype,但类里定义的方法,比如 class A { run() {} } 里的 A.prototype.run,是简写方法,没有 prototype,不能 new。
试着用自己的话回答

面试官还会怎么问?

Function.prototype 和函数的 prototype 属性是一回事吗?

不是。Function.prototype 是所有函数的原型,call、apply、bind 就定义在它上面,箭头函数也继承自它,所以箭头函数也能调用 call。而 Foo.prototype 是 Foo 自己的属性,给 Foo 的实例用。

bind 之后的构造函数还能 new 吗?

能。new 会忽略 bind 绑定的 this,但保留预置的参数,实例的原型是原函数的 prototype,所以 instanceof 原函数为 true。

箭头函数能用 call 改 this 吗?

能调用 call,但改不了 this。传进去的第一个参数会被忽略,箭头函数里的 this 始终是定义它的外层作用域的 this。

从一道题,走向一组知识

把知识连起来

函数与作用域

生成器函数是怎么工作的?yield 和 next 是什么关系?

生成器函数的 prototype 是它生成的迭代器对象的原型,看懂生成器怎么工作就明白这个属性为什么存在。

函数与作用域

生成器对象和数组这种可迭代对象有什么不一样?

生成器对象上的 next、return、throw 方法,就是沿着生成器函数的 prototype 链找到的。

参考资料

  • JavaScript:函数与作用域参考资料
  • Function.prototype.prototype - JavaScript | MDN

示例用于理解所注明的运行环境与边界;延伸学习可结合原文中的更多案例。

本题目录
  1. 先记住这个答案
  2. 把几类函数放在一起对比
  3. 为什么这些函数被设计成不能 new
  4. 容易答错的地方
  5. 面试官还会怎么问
  6. 把知识连起来
读懂,再试着讲出来

先看核心答案,再读代码。最后展开追问,检查自己有没有遗漏边界。

试着回答追问
浏览全部面试题理解原理,也关注真实的使用场景。回到顶部 ↑