从babel编译结果分析class的实现原理
示例:
class A {
// 属性表达式
prop1 = 1;
// get方法
get value() {
console.log('Getting the current value!');
return this.prop1;
}
// set方法
set value(newValue) {
console.log('Setting the current value!');
this.prop1 = newValue;
}
// 箭头函数表达式
arrowFunc = (...args) => {
console.log(args);
}
// constructor
constructor(b = 2) {
this.prop2 = b;
}
// 普通函数表达式
Func() {
console.log("Func");
}
// 静态属性
static prop3 = 3;
// 静态普通函数
static staticFunc() {
console.log("staticFunc", this);
}
// 静态箭头函数
static staticArrowFunc = () => {
console.log("staticArrowFunc", this);
}
}
const a = new A(3);
使用babel编译成es5的代码,编译结果会生成几个内部函数:
// 类的调用检查,如果调用A不使用new,则会报错
function _classCallCheck(instance, Constructor) {
if (!(instance instanceof Constructor)) {
throw new TypeError("Cannot call a class as a function");
}
}
// 属性描述符默认配置为不可枚举
function _defineProperties(target, props) {
for (var i = 0; i < props.length; i++) {
var descriptor = props[i];
descriptor.enumerable = descriptor.enumerable || false;
descriptor.configurable = true;
if ("value" in descriptor) descriptor.writable = true;
Object.defineProperty(target, descriptor.key, descriptor);
}
}
// 定义原型上的普通函数、静态普通函数、get和set方法
function _createClass(Constructor, protoProps, staticProps) {
if (protoProps) _defineProperties(Constructor.prototype, protoProps);
if (staticProps) _defineProperties(Constructor, staticProps);
return Constructor;
}
// 定义属性到obj上,重新赋值使用defineProperty,第一次赋值直接添加属性
function _defineProperty(obj, key, value) {
if (key in obj) {
Object.defineProperty(obj, key, {
value: value,
enumerable: true,
configurable: true,
writable: true
});
} else {
obj[key] = value;
}
return obj;
}
类的编译结果:
// A是一个立即执行函数 返回结果是个函数 函数名就是类名
var A = /*#__PURE__*/ (function () {
// constructor
function A() {
// 转化constructor中的默认参数
var b =
arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : 2;
// 检查类是否使用new执行
_classCallCheck(this, A);
// 属性表达式定义到类实例上
_defineProperty(this, "prop1", 1);
// 箭头函数表达式定义到类实例上
_defineProperty(this, "arrowFunc", function () {
// 这个for循环是转换...args,遍历arguments,将每一项赋值给args对象
for (
var _len = arguments.length, args = new Array(_len), _key = 0;
_key < _len;
_key++
) {
args[_key] = arguments[_key];
}
console.log(args);
});
this.prop2 = b;
} _createClass(
A,
[
{// get和set方法
key: "value",
get:
function get() {
console.log("Getting the current value!");
return this.prop1;
},
set: function set(newValue) {
console.log("Setting the current value!");
this.prop1 = newValue;
}
},
{// 普通函数表达式
key: "Func",
value: function Func() {
console.log("Func");
}
}
],
[
{// 静态普通函数
key: "staticFunc",
value: function staticFunc() {
console.log("staticFunc", this);
}
}
]
); return A;
})();
// 静态属性定义到类上
_defineProperty(A, "prop3", 3);
// 静态箭头函数定义到类上
_defineProperty(A, "staticArrowFunc", function () {
console.log("staticArrowFunc", A);
}); var a = new A(3);
下图可描述整个编译结果:

需要注意的是:
- 类原型上的方法、类的静态方法、类的get和set方法默认是不可枚举的
- 类实例上的方法和属性、类的静态箭头函数是可枚举的
之后再出一章class继承的相关内容
从babel编译结果分析class的实现原理的更多相关文章
- KoaHub.js可借助 Babel 编译稳定运行在 Node.js 环境上
koahubjs KoaHub.js -- 基于 Koa.js 平台的 Node.js web 快速开发框架.可以直接在项目里使用 ES6/7(Generator Function, Class, A ...
- 使用babel编译es6
起因:开发中慢慢的学习使用es6,但是JavaScript需要浏览器来解析,而不是所有浏览器都支持es6,所以为了兼容es6,需要第三方工具进行编译es6. 工具:node,gulp,gulp-bab ...
- React系列文章:Babel编译JSX生成代码
上次我们总结了React代码构建后的Webpack模块组织关系,今天来介绍一下Babel编译JSX生成目标代码的一些规则,并且模拟整个生成的过程. 我们还是拿最简单的代码举例: import {gre ...
- 持续集成篇_08_Hudson持续集成服务器的使用(自动化编译、分析、打包、部署)
持续集成篇_08_Hudson持续集成服务器的使用(自动化编译.分析.打包.部署) 1.创建任务 svn用户验证 验证通过 *****五颗*表示每分钟检查svn路径是否有变更,有变更就会重新构建,相当 ...
- webpack打包调试react并使用babel编译jsx配置方法
http://lxj8749.iteye.com/blog/2287074 ********************************************** 安装webpack npm i ...
- es6 babel编译
本文主要参照阮一峰的es6入门,为提高自己写了一份随笔. 原文地址请戳这里 ECMAScript 6 入门 ECMAScript 6是JavaScript语言的下一代标准.因为当前版本的ES6是在2 ...
- jrtplib源码分析 第一篇 jthread的编译与分析
第一篇 jthread的编译与分析 jrtplib代码依赖库jthread,因此先从jthread开始jrtplib的学习.首先从以下链接下载jthread的源代码http://research.ed ...
- 编译调试 .NET Core 5.0 Preview 并分析 Span 的实现原理
很久没有写过 .NET Core 相关的文章了,目前关店在家休息所以有些时间写一篇新的
- jQuery 2.0.3 源码分析Sizzle引擎解析原理
jQuery 2.0.3 源码分析Sizzle引擎 - 解析原理 声明:本文为原创文章,如需转载,请注明来源并保留原文链接Aaron,谢谢! 先来回答博友的提问: 如何解析 div > p + ...
- ILSpy,DLL反编译工具,学习与了解原理的好帮手
你是否一直苦于找到了好的dll却只知道怎么使用而不知道其原理. 你是否在使用一个dll的时候发现它在一些参数时报错了却没法解决. 你是否想成为一个优秀的.net开发,成为一个优秀的系统制造者. 那你需 ...
随机推荐
- 如何判断JS数据类型
在 ECMAScript 规范中,共定义了 7 种数据类型,分为 基本类型 和 引用类型 两大类,如下所示: 基本类型:String.Number.Boolean.Symbol.Undefined.N ...
- Python冰墩墩(非原创,搬运工)
import turtle turtle.title('2022北京冬奥会冰墩墩') turtle.speed(10000) # 速度 # 左手 turtle.penup() turtle.goto( ...
- Linux C语言编程基础
Linux C语言编程基础 选择教材第二章的一节进行编程基础练习 二叉树广度优先遍历(链队) 算法: "head.h" #ifndef _head_h_ #define _head ...
- Linux 使用Squid部署代理缓存服务
代理缓存服务 Squid是Linux系统中最为流行的一款高性能代理服务软件,通常用作Web网站的前置缓存服务,能够代替用户向网站服务器请求页面数据并进行缓存.简单来说,Squid服务程序会按照收到的用 ...
- C# 使用Enumerable.Range 打印数字
static void Main(string[] args) { var list1 = Enumerable.Range(0, (int)Math.Pow(2, 22)).ToList(); va ...
- Oracle关联表进行修改操作(查询某个表,以某个表作为基础,修改其它表)
merge into tableA a using( SELECT a,b,c from tableB ) b on (a.id = b.id)//这里一定要用括号包起来.... when match ...
- windows 10 的VMware workstation Pro突然变成英文界面
电脑的VMware虚拟机界面是中文版的,后来在捣弄些电脑配置,突然变成英文版界面了. 后面发现原来是区域格式选错了:正确的格式是下图红框
- 面向对象1(Java)
什么是面向对象 面向对象编程(oop) 面向对象编程的本质是:以类的方式组织代码,以对象的组织(封装)数据 抽象 三大特征:封装.继承.多态 从认识论角度考虑是先有对象后有类.对象是具体的事物.类是抽 ...
- Java 数据库表关联更新
SqlServer 关联更新语句: update a set a.pname = b.name from 表a a inner join 表b b on a.pid = b.id MySQL 关联更新 ...
- JMeter参数化(一)--CSV参数化
一.CSV Data Set Config 1.添加配置元件-CSV Data Set Config 其中,分隔符不能是参数化的值中的符号,否则会被截断. 2.调用 3.循环读取文件中数据 假设数据内 ...