查漏补缺 - 构造函数,原型,this,原型链,继承
目录
- 1,构造函数
- 2,原型
- 3,this
- 4,原型链
- 1,特点
- 2,Object.prototype.toString()
- 3,instanceof 运算符
- 4,Object.getPrototypeOf()
- 5,创建空原型对象
- 6,面试题
- 5,继承
- 封装继承
1,构造函数
1,作用:创建对象。
通过普通函数返回对象:
function createPerson(firstName, lastName) {var obj = {}obj.firstName = firstNameobj.lastName = lastNameobj.fullName = firstName + lastNameobj.myName = function () {console.log(obj.fullName)}return obj
}const person = createPerson('张', '三')
通过构造函数创建对象
function Person(firstName, lastName) {this.firstName = firstNamethis.lastName = lastNamethis.fullName = firstName + lastNamethis.myName = function () {console.log(this.fullName)}
}const person = new Person('张', '三') // 规定语法
2,js 中所有的对象,都是通过构造函数创建的。
Object() 构造函数,所以 typeof Object === 'function'
var obj = {age: 18
}// 上面是语法糖var obj = new Object()
obj.age = 18
Function()构造函数
每个 js 函数实际上都是一个 Function 对象,通过 Function 构造函数创建时(可以不加 new 关键字)。
const add= new Function("a", "b", "return a + b");
add(2, 6);
2,原型
当构造函数中定义方法时,因为每个构造出的实例都是独立的,所以每次也会创建一个新的方法。
function Foo(a, b) {this.a = athis.b = bthis.sayHi = function () {console.log(this.a + this.b)}
}const foo1 = new Foo(1, 2)
const foo2 = new Foo(1, 2)console.log(foo1.sayHi === foo2.sayHi) // false
这会造成内存空间的浪费,所以出现了原型来解决这个问题。
当访问实例成员时,先找自身,如果不存在,会自动从隐式原型中寻找。
原型也是一个对象,一般会将公共的方法放到原型上。
function Foo(a, b) {this.a = athis.b = b
}Foo.prototype.sayHi = function () {console.log(this.a + this.b)
}const foo1 = new Foo(1, 2)
const foo2 = new Foo(1, 2)console.log(foo1.sayHi === foo2.sayHi) // true

3,this
1,在函数中使用 this,它的指向完全取决于函数是如何调用的。具体参考
例子,为所有对象添加方法 print,并打印对象的键值对。
Object.prototype.print = function () {for (var key in this) {// 过滤掉 printif (this.hasOwnProperty(key)) {console.log(key, this[key])}}
}var obj = {a: 1,b: 2
}console.log(obj.print())
2,hasOwnProperty
表示对象自有属性(而不是继承来的属性)中是否具有指定的属性。
3,in 运算符
判断属性名是否在对象自身及其原型链上。
4,原型链

1,特点
-
在
Object.prototype上添加属性,会影响到所有对象,包括函数和数组。 -
在
Function.prototype上添加属性,会有影响到所有函数,所以可以判断一个变量是不是函数。
Function.prototype.isFun = truevar obj = {}
function fun() {}console.log(obj.isFun) // undefined
console.log(fun.isFun) // true
2,Object.prototype.toString()
MDN - Object.prototype.toString()
会把对象转为字符串格式 [object Object],但这种格式并不是每个对象想要的。
所以数组重写了 toString 方法
Array.prototype.toString === Object.prototype.toString // false
如何让数组的 toString 方法使用 Object.prototype.toString
const arr = [1,2,3]
Object.prototype.toString.call(arr)
所以判断一个变量是不是数组的方法:
const arr = [];
console.log(Object.prototype.toString.call(arr)); // [object Array]
如果自己的构造函数希望改变 toString,如何改变?
function User() {}
const user = new User();User.prototype.toString = function () {return "xxx";
};console.log(user.toString()); // xxx
3,instanceof 运算符
MDN - instanceof 运算符
用于检测构造函数的 prototype,是否出现在某个实例对象的原型链上。
function User() {}var user = new User()console.log(user instanceof User) // true
console.log(user instanceof Object) // true
o in C 更多的用来判断对象 o 是不是构造函数 C 的创建的实例。
所以,可以这样理解:
obj instanceof Array // obj 是不是数组
obj instanceof Object // obj 是不是对象
obj instanceof Function // obj 是不是函数
4,Object.getPrototypeOf()
Object.getPrototypeOf()
因为不推荐使用 __proto__,所以有了新的方法来操作隐式原型:Object.getPrototypeOf() 和 Object.setPrototypeOf()
const arr = [];
console.log(Object.getPrototypeOf(arr) === arr.__proto__); // true
5,创建空原型对象
方法1,
const obj = {}
obj.__proto__ = null // 不推荐 直接操作 __proto__Object.setPrototypeOf(obj, null) // 可以使用
方式2,
const obj = Object.create(null)
6,面试题
下面的面试题,都可以用上面的原型链图快速解释。
// 下面的代码输出什么?(京东)
Function.prototype.a = 1;
Object.prototype.b = 2;function A() {}var a = new A();console.log(a.a, a.b); // undefined 2
console.log(A.a, A.b); // 1 2
// 下面的代码输出什么?(字节)
console.log({} instanceof Object); // true
console.log({}.toString instanceof Function); // true
console.log(Object instanceof Function); // true
console.log(Function instanceof Object); // true
// 下面的代码输出什么?
function User() {}
User.prototype.sayHello = function () {};var u1 = new User();
var u2 = new User();console.log(u1.sayHello === u2.sayHello); // true
console.log(User.prototype === Function.prototype); // false
console.log(User.__proto__ === Function.prototype); // true
console.log(User.__proto__ === Function.__proto__); // true
console.log(u1.__proto__ === u2.__proto__); // true
console.log(u1.__proto__ === User.__proto__); // false
console.log(Function.__proto__ === Object.__proto__); // true
console.log(Function.prototype.__proto__ === Object.prototype.__proto__); // false
console.log(Function.prototype.__proto__ === Object.prototype); // true
5,继承
假设有一个会员系统
- 免费用户
- 属性:用户名,密码
- 方法:播放免费视频
- vip 用户
- 属性:还有会员过期时间
- 方法:还有播放vip视频
function User(name, pwd) {this.name = namethis.pwd = pwd
}User.prototype.playFreeVideo = function() {console.log('免费视频');
}function VipUser(name, pwd, expires) {this.name = namethis.pwd = pwdthis.expires = expires
}VipUser.prototype.playFreeVideo = function() {console.log('免费视频');
}VipUser.prototype.playVipVideo = function() {console.log('vip视频');
}
可以看到有冗余的代码。改造下
1,处理构造函数内部的重复。
function VipUser(name, pwd, expires) {User.call(this, name, pwd)this.expires = expires
}
2,处理原型上的重复
需要一个图来表现关系
// VipUser.prototype.__proto__ = User.prototype
Object.setPrototypeOf(VipUser.prototype, User.prototype)
继承就是上面这种关系。
- 子类的实例,应该自动拥有父类的所有成员。
- 子类最多只有一个父类
- 间接父类的成员,会传递给子类
封装继承
function inherit(Child, Parent) {Object.setPrototypeOf(Child.prototype, Parent.Parent)
}
相关文章:
查漏补缺 - 构造函数,原型,this,原型链,继承
目录 1,构造函数2,原型3,this4,原型链1,特点2,Object.prototype.toString()3,instanceof 运算符4,Object.getPrototypeOf()5,创建空原型对象6,面试题 5&#…...
C# 学习笔记--个人学习使用 <2>
C# 学习笔记 Chapter 2 比较硬的基础部分Section 1 委托Part 1 Action 与 func 委托的示例Part 2 自定义委托Part 3 委托的一般使用Part 4 委托的高级使用Part 5 适时地使用接口 Interface 取代一些对委托的使用 Section 2 事件Part 1 初步了解事件Part 2 事件的应用Part 3 事件…...
Linux网络编程Socket通信6-Libevent移植与使用
目录 libeventlibevent交叉编译并移植libevent安装安装步骤测试代码libevent执行报错解决 libevent_base根节点event_base_newevent_base_freeevent_reinit event_loop循环等待事件event_base_loopevent_base_dispatchevent_base_loopexitevent_base_loopbreak event事件event_…...
c#:委托 泛型委托的使用 泛型约束
委托 在 C# 中,delegate 是一种引用类型,它允许您定义和使用可以引用特定方法的对象。delegate 可以看作是一种函数指针,它可以在运行时动态地调用不同的方法。 以下是一个简单的例子来说明 delegate 的实际作用: // 1. 定义一…...
大数据之linux入门
一、linux是什么 linux操作系统 开发者是林纳斯-托瓦兹,出于个人爱好编写。linux是一个基于posix和unix的多用户、多任务、支持多线程和多CPU的操作系统。 Unix是20世纪70年代初出现的一个操作系统,除了作为网络操作系统之外,还可以作为单…...
MPI之MPI_Sendrecv接口以及空进程概念介绍
MPI_Sendrecv函数原型 int MPI_Sendrecv(const void *sendbuf, int sendcount, MPI_Datatype sendtype, int dest, int sendtag,void *recvbuf, int recvcount, MPI_Datatype recvtype, int source, int recvtag, MPI_Comm comm, MPI_Status *status);其中各个参数的含义如下&…...
Revit SDK:PointCurveCreation 创建点来拟合曲线
前言 这个例子通过留个例子来展示如何通过点来拟合曲线或者曲面。 内容 PointsParabola 生成抛物线的核心逻辑: double yctr 0; XYZ xyz null; ReferencePoint rp null; double power 1.2; while (power < 1.5){double xctr 0;double zctr 0;while (…...
嵌入式Linux开发实操(十五):nand flash接口开发
# 前言 flash memory,分NAND和NOR: 如果说nor flash有个特点就是能执行代码,NOR并行接口具有地址和数据总线,spi flash更是主要用于存储代码,SPI(或QSPI)NOR代码可就地执行(XiP),一般系统要求flash闪存提供相对较高的频率和数据缓存的clocking。而nand flash主要用于…...
vue2 组件库之vetur提示
当我们开发完自定义UI组件库后,在项目中使用时,想要达到以下提示效果,组件提示与属性提示,有什么解决方案呢: 事实上,这是vetur的功能,原文如下: Component Data | Vetur If a pac…...
慕课网 Go工程师 第三周 package和gomodules章节
Go包的引入: 包名前面加匿名,只引入但不使用,如果对应包有init函数,会执行init函数(初始化操作) 包名前面加. 把这个包的结构体和方法导入当前包,慎用,你不知道当前包和被引入的包用…...
【ES6】JavaScript 中的数组方法reduce
reduce() 是一个 JavaScript 中的数组方法,它会对数组的每个元素执行一个提供的 reducer 函数,将其减少到一个单一的值。 这是 reduce() 的基本用法: //(method) Array<number>.reduce(callbackfn: (previousValue: number, currentV…...
数据结构--树4.2(二叉树)
目录 一、二叉树的定义和特点 1、定义 2、特点 二、二叉树的基本形态 1、空二叉树 2、只有一个根结点 3、根结点只有左子树 4、根结点只有右子树 5、根结点既有左子树又有右子树 6、斜树 7、满二叉树 8、满二叉树和完全二叉树 三、二叉树的性质 一、二叉树的定义和…...
详解Numpy(基于jupyter notbook)
详解Numpy(基于jupyter notbook) 1.创建数组2.数据类型3.数组切片和索引4.Numpy的广播与数组操作5.数组合并与通用函数6.其他通用函数 1.创建数组 #引入numpy包,以后np就代表numpy import numpy as npanp.arange(10,30,2)#10为起点ÿ…...
uniapp实现:点击拨打电话,弹出电话号码列表,可以选择其中一个进行拨打
一、实现效果: 二、代码实现: 在uni-app中,使用uni.showActionSheet方法实现点击拨打电话的功能,并弹出相关的电话列表供用户选择。 当用户选择了其中一个电话后,会触发success回调函数,并通过res.tapInde…...
swc-loader Segmentation fault “$NODE_EXE“ “$NPM_CLI_JS“ “$@“
webpack swc swc还不是很稳定。 在swcrc 中有配置plugins 时,swc 转换 /node_modules/ 会报错。 环境 swc/cor1.3.62swc-loader0.2.3swc-plugin-vue-jsx0.2.5 解决 配两套rule,一套处理项目代码,一套处理node_modules webpack.config.js rules:…...
Leetcode78. 子集
给你一个整数数组 nums ,数组中的元素 互不相同 。返回该数组所有可能的子集(幂集)。 解集 不能 包含重复的子集。你可以按 任意顺序 返回解集。 回溯法 class Solution {public List<List<Integer>> subsets(int[] nums) {List…...
百度“AI智障”到AI智能体验之旅
目录 前言一、百度PLATO1.抬杠第一名2.听Ta瞎扯淡3.TA当场去世了4.智障与网友的高光时刻 二、文心一言1.设计测试用例2.随意发问3.手机端约会神器 三、体验总结:四、千帆大模型 前言 最近收到了文心一言3.5大模型的内测资格,正巧之前也体验过它的前身&q…...
R中当并行运算遇到C++函数时,让foreach+Rcpp一起工作
目录 方案一:C函数在R包中 方案二:C函数在本地,通过Rcpp::sourceCpp("fun_name.cpp")使用 方案三:将C函数写在当前脚本中 题外话:为什么要研究foreachRcpp? 本文参考: 问题:在fo…...
实现带头双向循环链表
🌈带头双向循环链表 描述:一个节点内包含两个指针,一个指向上一个节点,另一个指向下一个节点。哨兵位指向的下一个节点为头节点,哨兵位的上一个指向尾节点。 结构优势:高效率找尾节点;高效率插入…...
Mysql 表字符集变更
背景 线上有几张表的字符集是 latin1,要求换成utf8mb4。至于操作的时机则需要自行判断。 1.查看库中所有字符集为latin1的所有表 SELECTDISTINCTtable_schema,table_name,collation_name,character_set_name,CONCAT(ALTER TABLE , table_schema, ., table_name, …...
UE5 学习系列(二)用户操作界面及介绍
这篇博客是 UE5 学习系列博客的第二篇,在第一篇的基础上展开这篇内容。博客参考的 B 站视频资料和第一篇的链接如下: 【Note】:如果你已经完成安装等操作,可以只执行第一篇博客中 2. 新建一个空白游戏项目 章节操作,重…...
1688商品列表API与其他数据源的对接思路
将1688商品列表API与其他数据源对接时,需结合业务场景设计数据流转链路,重点关注数据格式兼容性、接口调用频率控制及数据一致性维护。以下是具体对接思路及关键技术点: 一、核心对接场景与目标 商品数据同步 场景:将1688商品信息…...
2025 后端自学UNIAPP【项目实战:旅游项目】6、我的收藏页面
代码框架视图 1、先添加一个获取收藏景点的列表请求 【在文件my_api.js文件中添加】 // 引入公共的请求封装 import http from ./my_http.js// 登录接口(适配服务端返回 Token) export const login async (code, avatar) > {const res await http…...
使用 SymPy 进行向量和矩阵的高级操作
在科学计算和工程领域,向量和矩阵操作是解决问题的核心技能之一。Python 的 SymPy 库提供了强大的符号计算功能,能够高效地处理向量和矩阵的各种操作。本文将深入探讨如何使用 SymPy 进行向量和矩阵的创建、合并以及维度拓展等操作,并通过具体…...
C++:多态机制详解
目录 一. 多态的概念 1.静态多态(编译时多态) 二.动态多态的定义及实现 1.多态的构成条件 2.虚函数 3.虚函数的重写/覆盖 4.虚函数重写的一些其他问题 1).协变 2).析构函数的重写 5.override 和 final关键字 1&#…...
腾讯云V3签名
想要接入腾讯云的Api,必然先按其文档计算出所要求的签名。 之前也调用过腾讯云的接口,但总是卡在签名这一步,最后放弃选择SDK,这次终于自己代码实现。 可能腾讯云翻新了接口文档,现在阅读起来,清晰了很多&…...
三分算法与DeepSeek辅助证明是单峰函数
前置 单峰函数有唯一的最大值,最大值左侧的数值严格单调递增,最大值右侧的数值严格单调递减。 单谷函数有唯一的最小值,最小值左侧的数值严格单调递减,最小值右侧的数值严格单调递增。 三分的本质 三分和二分一样都是通过不断缩…...
BLEU评分:机器翻译质量评估的黄金标准
BLEU评分:机器翻译质量评估的黄金标准 1. 引言 在自然语言处理(NLP)领域,衡量一个机器翻译模型的性能至关重要。BLEU (Bilingual Evaluation Understudy) 作为一种自动化评估指标,自2002年由IBM的Kishore Papineni等人提出以来,…...
DeepSeek源码深度解析 × 华为仓颉语言编程精粹——从MoE架构到全场景开发生态
前言 在人工智能技术飞速发展的今天,深度学习与大模型技术已成为推动行业变革的核心驱动力,而高效、灵活的开发工具与编程语言则为技术创新提供了重要支撑。本书以两大前沿技术领域为核心,系统性地呈现了两部深度技术著作的精华:…...
React核心概念:State是什么?如何用useState管理组件自己的数据?
系列回顾: 在上一篇《React入门第一步》中,我们已经成功创建并运行了第一个React项目。我们学会了用Vite初始化项目,并修改了App.jsx组件,让页面显示出我们想要的文字。但是,那个页面是“死”的,它只是静态…...
