文章目录
- Web前端面试题总结(二)JavaScript篇
- 1、JavaScript 是一门什么样的语言,它有哪些特点?
- 2、javascript 的本地对象,内置对象和宿主对象?
- 3、js 的内置对象有哪些?列举一下 arry 和 string 的常用方法?
- 4、例举 3 种强制类型转换和 2 种隐式类型转换?
- 5、操作 DOM 的常用 API ?
- 6、BOM 之常用 API ?
- 7、prop 和 attr 的区别?
- 8、 typeof 和 instanceof 区别 ?
- 9、什么是闭包?
- 10、说说你对原型(prototype)理解 ?
- 11、介绍下原型链(解决的是继承问题吗)?
- 12、简单说说 js 中的继承 ?
- 13、介绍 this 各种情况?
- 14、数组中的 forEach 和 map 的区别?
- 15、for in 和 for of 的区别 ?
- 16、Call 和 apply,bind 的区别 ?
- 17、New 操作符具体干了什么呢?
- 18、用 js 实现随机选取 10–100 之间的 10 个数字,存入一 个数组并排序?
- 19、已知数组 var stringArray = [“This”,“is”, “Baidu”,“Campus”],Alert 出”This is Baidu Campus”
- 20、已知有字符串 foo=”get-element-by-id”,写一个 function 将其转化成驼峰 表示法”getElementById”
- 22、写一个 function,清除字符串前后的空格。(兼容所有 浏览器)
- 23、判断一个字符串中出现次数最多的字符,统计这个次数
- 24、Split()和 join()的区别?
- 25、js 数组去重,能用几种方法实现?
- 26、谈谈你对 Javascript 垃圾回收机制的理解?
- 27、js 如何处理防抖和节流?
- 28、如何判断 JavaScript 的数据类型?
- 29、创建对象有几种方法
- 30、=== 和 ==的区别?
- 写给看到最后的你
Web前端面试题总结(二)JavaScript篇
1、JavaScript 是一门什么样的语言,它有哪些特点?
javaScript 一种直译式脚本语言,是一种动态类型、弱类型、基于原型的语言,内置支持类型。它的解释器被称为 JavaScript 引擎,为浏览器的一部分,广泛用于客户端的脚本语言,最早是在 HTML 网页上使用,用来给HTML 网页增加动态功能。JavaScript 兼容于ECMA 标准,因此也称为ECMAScript。
基 本 特 点
1.是一种解释性脚本语言(代码不进行预编译)。
2.主要用来向 HTML(标准通用标记语言下的一个应用)页面添加交互行为。
3.可以直接嵌入 HTML 页面,但写成单独的 js 文件有利于结构和行为的分离。
4.跨平台特性,在绝大多数浏览器的支持下,可以在多种平台下运行(如 Windows、Linux、Mac、Android、iOS 等)。
2、javascript 的本地对象,内置对象和宿主对象?
本地对象为 array obj regexp 等可以 new 实例化内置对象为 gload Math 等不可以实例化的
宿主为浏览器自带的 document,window 等
3、js 的内置对象有哪些?列举一下 arry 和 string 的常用方法?
JavaScript 常见的内置对象有 Object,Math,String,Array,Number,Function,Boolean,JSON 等,其中 Object
是所有对象的基类,采用了原型继承方式.
String:charAt(); charCodeAt(); indexOf(); match(); replace(); search(); slice(); toUpperCase(); toLowerCase(); 等方法
Array:shift(); unshift(); pop(); push(); concat(); reverse(); splice(); slice(); 等方法
4、例举 3 种强制类型转换和 2 种隐式类型转换?
强制:parseInt()、parseFloat()、Number() 隐式:== 、console.log()、alert()
5、操作 DOM 的常用 API ?
1.节 点 查 找 document.getElementById…
2.节点创建. createElement cloneNode… 3.节点修改 appendChild insertBefore RemoveChild replaceChild…
4.元素属性型 setAttribute getAttribute…
6、BOM 之常用 API ?
navigator:window 中封装浏览器属性和配置信息的对象cookieEnabled:识别浏览器是否启用 cookie,返回值 true/false userAgent:保存了浏览器名称和版本的字符串
plugins:保存浏览器中所有插件信息的集合,每个 plugin 对象的 name 属性保存了插件的名称
screen:保存显示屏信息的对象 history:保存窗口的历史记录栈 location:指代当前窗口正在访问的 url 地址对象
location.href:保存了当前窗口正在访问的 url 地址,设置 href 属性为新 url,会在当前窗口打开新的地址页面
location.search():获取 url 上面 ?后面的参数
location.reload():刷新当前页面
location.assign(url):设置当前窗口的新 url
location.reload(true/false):true —— 无论是否更改,都获取更新;false —— 被修改的页面,重新获取,未被修改的页面,从缓冲获取定时器:让程序按指定时间间隔,自动执行任务,任务是所有定时器的核心
7、prop 和 attr 的区别?
对于 HTML 元素本身就带有的固有属性,在处理时,使用 prop 方法。
对于 HTML 元素我们自己自定义的 DOM 属性,在处理时,使用 attr 方法。
栗子 1:
<a href="http://www.baidu.com" target="_self" class="btn">百度</a>
这个例子里a元素的 DOM 属性有“href、target 和 class",这些属性就是a元素本身就带有的属性,也是 W3C 标准里就包含有这几个属性,或者说在 IDE 里能够智能提示出的属性,这些就叫做固有属性。处理这些属性时,建议使用 prop 方法。
<a href="#" id="link1" action="delete">删除</a>
这个例子里a元素的 DOM 属性有“href、id 和 action”,很明显,前两个是固有属性,而后面一个“action”属性是我们自己自定义上去的,a元素本身是没有这个属性的。这种就是自定义的 DOM 属性。处理这些属性时,建议使用 attr 方法。
8、 typeof 和 instanceof 区别 ?
在 javascript 中,判断一个变量的类型可以用 typeof
1、数字类型、typeof 返回的值是 number。比如说:typeof(1),返回值是 number 2、字符串类型,typeof 返回的值是 string。比如 typeof(“123”返回值时 string) 3、布尔类型,typeof 返回的值是 boolean。比如 typeof(true)返回值时 boolean 4、对象、数组、null 返回的值是 object。比如 typeof(window),typeof(document),typeof(null)
返回的值都是 object
5、函数类型,返回的值是 function。比如:typeof(eval),typeof(Date)返回的值都是 function。 6、不存在的变量、函数或者 undefined,将返回 undefined。比如:typeof(abc)、typeof(undefined)
都返回 undefined
在 javascript 中,instanceof 用于判断某个对象是否被另一个函数构造
使用 typeof 运算符时采用引用类型存储值会出现一个问题,无论引用的是什么类型的对象,它都 返回”object”。ECMAScript 引入了另一个 Java 运算符 instanceof 来解决这个问题。Instanceof 运算 符与 typeof 运算符相似,用于识别正在处理的对象的类型。与 typeof 方法不同的是,instanceof 方法要求开发者明确地确认对象为某特定类型
9、什么是闭包?
“闭包就是能够读取其他函数内部变量的函数。例如在 javascript 中,只有函数内部的子函数 才能读取局部变量,所以闭包可以理解成“定义在一个函数内部的函数“。在本质上,闭包是将函 数内部和函数外部连接起来的桥梁。”
举例:创建闭包最常见方式,就是在一个函数内部创建另一个函数。下面例子中的 closure 就 是一个闭包,
function func(){
var a =1 ,b = 2;
funciton closure(){ return a+b; } return closure; }
10、说说你对原型(prototype)理解 ?
JavaScript 是一种通过原型实现继承的语言与别的高级语言是有区别的,像 java,C#是通 过类型决定继承关系的,JavaScript 是的动态的弱类型语言,总之可以认为 JavaScript 中所有 都是对象,在 JavaScript 中,原型也是一个对象,通过原型可以实现对象的属性继承,JavaScript 的对象中都包含了一个” prototype”内部属性,这个属性所对应的就是该对象的原型
“prototype”作为对象的内部属性,是不能被直接访问的。所以为了方便查看一个对象的原 型,Firefox 和 Chrome 内核的 JavaScript 引擎中提供了”proto“这个非标准的访问器(ECMA 新 标准中引入了标准对象原型访问器”Object.getPrototype(object)”)
原型的主要作用就是为了实现继承与扩展对象
11、介绍下原型链(解决的是继承问题吗)?
JavaScript 原型: 每个对象都会在其内部初始化一个属性,就是 prototype(原型) 原型链:
当我们访问一个对象的属性时,如果这个对象内部不存在这个属性,那么他就会去 prototype 里找这个属性,这个 prototype 又会有自己的 prototype,于是就这样一直找下去, 也就是我们平时所说的原型链的概念
特点:
JavaScript 对象是通过引用来传递的,我们创建的每个新对象实体中并没有一份属于自己 的原型副本。当我们修改原型时,与之相关的对象也会继承这一改变
12、简单说说 js 中的继承 ?
继承有以下六种方法
1、原型链继承 JavaScript 实现继承的基本思想:通过原型将一个引用类型继承另一个引用 类型的属性和方法
2、借用构造函数继承(伪造对象或经典继承) JavaScript 实现继承的基本思想:在子类构造 函数内部调用超类型构造函数。 通过使用 apply()和 call()方法可以在新创建的子类对象上执行构造函数
3、组合继承(原型+借用构造)(伪经典继承) JavaScript 实现继承的基本思想:将原型链和借 用构造函数的技术组合在一块,从而发挥两者之长的一种继承模式 将原型链和借用构造函数的技术组合到一起,从而取长补短发挥两者长处的一种继承模式 4、型式继承 JavaScript 实现继承的基本思想:借助原型可以基于已有的对象创建新对象, 同时还不必须因此创建自定义的类型
5、寄生式继承 JavaScript 实现继承的基本思想:创建一个仅用于封装继承过程的函数,该 函数在内部以某种方式来增强对象,最后再像真正是它做了所有工作一样返回对象。 寄生式继承是原型式继承的加强版
6、寄生组合式继承 JavaScript 实现继承的基本思想:通过借用函数来继承属性,通过原型 链的混成形式来继承方法
13、介绍 this 各种情况?
this 的情况:
1、以函数形式调用时,this 永远都是 window 2、以方法的形式调用时,this 是调用方法的对象 3、以构造函数的形式调用时,this 是新创建的那个对象 4、使用 call 和 apply 调用时,this 是指定的那个对象 5、箭头函数:箭头函数的 this 看外层是否有函数
如果有,外层函数的 this 就是内部箭头函数的 this
如果没有,就是 window
6、特殊情况:通常意义上 this 指针指向为最后调用它的对象。这里需要注意的一点就是
如果返回值是一个对象,那么 this 指向的就是那个返回的对象,如果返回值不是一个对象那么 this 还是指向函数的实例
14、数组中的 forEach 和 map 的区别?
forEach 和 map 的相同点
相同点 都是循环遍历数组中的每一项
forEach 和 map 方法里每次执行匿名函数都支持 3 个参数,参数分别是 item(当前每一项), index(索引值),arr(原数组)
匿名函数中的 this 都是指向 window 只能遍历数组 都不会改变原数组 区别:
map 方法
1.map 方法返回一个新的数组,数组中的元素为原始数组调用函数处理后的值
2.map 方法不会对空数组进行检测,map 方法不会改变原始数组。 3.浏览器支持:chrome、Safari1.5+、opera 都支持,IE9+, 若 arr 为空数组,则 map 方法返 回的也是一个空数组。
forEach 方法
1.forEach 方法用来调用数组的每个元素,将元素传给回调函数
2.forEach 对于空数组是不会调用回调函数的。 无论 arr 是不是空数组,forEach 返回的都是 undefined。这个方法只是将数组中的每一项作为 callback 的参数执行一次
15、for in 和 for of 的区别 ?
1、推荐在循环对象属性的时候使用 for…in,在遍历数组的时候的时候使用 for…of
2、for…in 循环出的是 key,for…of 循环出的是 value
3、注意,for…of 是 ES6 新引入的特性。修复了 ES5 引入的 for…in 的不足
4、for…of 不能循环普通的对象,需要通过和 Object.keys()搭配使用
16、Call 和 apply,bind 的区别 ?
call 方法调用一个函数, 其具有一个指定的 this 值和分别地提供的参数(参数的列表)。 注意:该方法的作用和 apply() 方法类似,只有一个区别,就是 call()方法接受的是若干个 参数的列表,而 apply()方法接受的是一个包含多个参数的数组
方法调用一个具有给定 this 值的函数,以及作为一个数组(或类似数组对象)提供的参数。 注意:call()方法的作用和 apply() 方法类似,区别就是 call()方法接受的是参数列表,而 apply() 方法接受的是一个参数数组
bind()方法创建一个新的函数,当这个新的函数被调用时,其 this 置为提供的值,其参数 列表前几项,置为创建时指定的参数序列
17、New 操作符具体干了什么呢?
1、创建一个空对象: 并且 this 变量引入该对象,同时还继承了函数的原型
2、设置原型链 空对象指向构造函数的原型对象
3、执行函数体 修改构造函数 this 指针指向空对象,并执行函数体
4、判断返回值 返回对象就用该对象,没有的话就创建一个对象
18、用 js 实现随机选取 10–100 之间的 10 个数字,存入一 个数组并排序?
function randomNub(aArray, len, min, max) {
if (len >= (max - min)) {
return '超过' + min + '-' + max + '之间的个数范围' + (max - min - 1) + '个 的总数';
}
if (aArray.length >= len) {
aArray.sort(function(a, b) {
return a - b
});
return aArray;
}
var nowNub = parseInt(Math.random() * (max - min - 1)) + (min + 1);
for (var j = 0; j < aArray.length; j++) {
if (nowNub == aArray[j]) {
randomNub(aArray, len, min, max);
return;
}
}
aArray.push(nowNub);
randomNub(aArray, len, min, max);
return aArray;
}
var arr=[];
randomNub(arr,10,10,100);
19、已知数组 var stringArray = [“This”,“is”, “Baidu”,“Campus”],Alert 出”This is Baidu Campus”
var stringArray = ["This", "is", "Baidu", "Campus"] alert(stringArray.join(""))
20、已知有字符串 foo=”get-element-by-id”,写一个 function 将其转化成驼峰 表示法”getElementById”
function combo(msg){
var arr=msg.split("-");
for(var i=1;i<arr.length;i++){ arr[i]=arr[i].charAt(0).toUpperCase()+arr[i].substr(1,arr[i].length-1); }
msg=arr.join("");
return msg;
}```
## 21、有这样一个 URL: http://item.taobao.com/item.htm?a=1&b=2&c=&d=xxx&e,请写 一段 JS 程序提取 URL 中的各个 GET 参数(参数名和参数个数不确定),将其按 key-value 形式返回到一个 json 结构中,如{a: "1", b: "2", c: "", d: "xxx", e: undefined}
```javascript
function serilizeUrl(url) {
var urlObject = {};
if (/\?/.test(url)) {
var urlString = url.substring(url.indexOf("?") + 1); var urlArray = urlString.split("&");
for (var i = 0, len = urlArray.length; i < len; i++) { var urlItem = urlArray[i];
var item = urlItem.split("=");
urlObject[item[0]] = item[1];
}
return urlObject; }
return null;
}
22、写一个 function,清除字符串前后的空格。(兼容所有 浏览器)
//使用自带接口 trim(),考虑兼容性:
if (!String.prototype.trim) {
String.prototype.trim = function() {
return this.replace(/^\s+/, "").replace(/\s+$/,"");
}
}
// test the function
var str = " \t\n test string ".trim(); alert(str == "test string"); // alerts "true"
23、判断一个字符串中出现次数最多的字符,统计这个次数
var str = 'asdfssaaasasasasaa';
var json = {};
for (var i = 0; i < str.length; i++) {
if(!json[str.charAt(i)]){ json[str.charAt(i)] = 1;
}else{ json[str.charAt(i)]++;
} };
var iMax = 0; var iIndex = ''; for(var i in json){
if(json[i]>iMax){ iMax = json[i]; iIndex = i;}}
alert('出现次数最多的是:'+ iIndex + '出现'+ iMax +'次')
24、Split()和 join()的区别?
Split()是把一串字符(根据某个分隔符)分成若干个元素存放在一个数组里 即切割成数组的形式;
join() 是把数组中的字符串连成一个长串,可以大体上认为是 Split()的逆操作
25、js 数组去重,能用几种方法实现?
1、使用 es6 set 方法 [...new Set(arr)] let arr = [1,2,3,4,3,2,3,4,6,7,6];
let unique = (arr)=> [...new Set(arr)];
unique(arr);//[1, 2, 3, 4, 6, 7]
2、利用新数组 indexOf 查找 indexOf() 方法可返回某个指定的元素在数组中首次出现的位置。 如果没有就返回-1。
3、for 双重循环 通过判断第二层循环,去重的数组中是否含有该元素,如果有就退出第二层循环,如果没有 j==result.length 就相等,然后把对应的元素添加到最后的数组里面。
let arr = [1,2,3,4,3,2,3,4,6,7,6];
let result = []; for(var i = 0 ; i< arr.length; i++) {
for(var j = 0 ; j < result.length ; j++)
{ if( arr[i] === result[j]){
break;};};
if(j == result.length){
result.push(arr[i]); };};
console.log(result);
4、利用 for 嵌套 for,然后 splice 去重 functionunique(arr){ for(vari=0; i<arr.length;
i++){ for(varj=i+1; j<arr.length; j++){ if(arr[i]==arr[j]){ //第一个等同于第二个,splice 方法删除第二个 arr.splice(j,1); j--; } } } returnarr; }
5、利用 filter
let arr = [1,2,3,4,3,2,3,4,6,7,6];
let unique = (arr) => {
return arr.filter((item,index) => {
return arr.indexOf(item) === index;
}) }; unique(arr);
6、let arr = [1,2,3,4,3,2,3,4,6,7,6];
let unique = (arr) => { return arr.filter((item,index) => {
return arr.indexOf(item) === index;
}) }; unique(arr);
7、利用 Map 数据结构去重
let arr = [1,2,3,4,3,2,3,4,6,7,6];
let unique = (arr)=> { let seen = new Map();
return arr.filter((item) => {
return !seen.has(item) && seen.set(item,1);
});
}; unique(arr);
26、谈谈你对 Javascript 垃圾回收机制的理解?
1、标记清除(mark and sweep)
这是 JavaScript 最常见的垃圾回收方式,当变量进入执行环境的时候,比如函数中声明一个变量, 垃圾回收器将其标记为“进入环境”,当变量离开环境的时候(函数执行结束)将其标记为“离开 环境” 垃圾回收器会在运行的时候给存储在内存中的所有变量加上标记,然后去掉环境中的变量以及被 环境中变量所引用的变量(闭包),在这些完成之后仍存在标记的就是要删除的变量了
2、引用计数(reference counting)
在低版本 IE 中经常会出现内存泄露,很多时候就是因为其采用引用计数方式进行垃圾回收。引 用计数的策略是跟踪记录每个值被使用的次数,当声明了一个 变量并将一个引用类型赋值给该 变量的时候这个值的引用次数就加 1,如果该变量的值变成了另外一个,则这个值得引用次数减 1,当这个值的引用次数变为 0 的时 候,说明没有变量在使用,这个值没法被访问了,因此可以 将其占用的空间回收,这样垃圾回收器会在运行的时候清理掉引用次数为 0 的值占用的空间
在 IE 中虽然 JavaScript 对象通过标记清除的方式进行垃圾回收,但 BOM 与 DOM 对象却是通过引 用计数回收垃圾的,也就是说只要涉及 BOM 及 DOM 就会出现循环引用问题
27、js 如何处理防抖和节流?
在进行窗口的 resize、scroll,输入框内容校验等操作时,如果事件处理函数调用的频率无限 制,会加重浏览器的负担,导致用户体验非常糟糕
此时我们可以采用 debounce(防抖)和 throttle(节流)的方式来减少调用频率,同时又不 影响实际效果
函数防抖: 函数防抖(debounce):当持续触发事件时,一定时间段内没有再触发事件,事件处理函数 才会执行一次,如果设定的时间到来之前,又一次触发了事件,就重新开始延时 如下,持续触发 scroll 事件时,并不执行 handle 函数,当 1000 毫秒内没有触发 scroll 事件时, 才会延时触发 scroll 事件
function debounce(fn, wait) {
var timeout = null;
return function() {
if(timeout !== null) clearTimeout(timeout); timeout = setTimeout(fn, wait);
} } // 处理函数 function handle() { console.log(Math.random()); }
// 滚动事件
window.addEventListener('scroll', debounce(handle, 1000));
函数节流(throttle):当持续触发事件时,保证一定时间段内只调用一次事件处理函数 节流通俗解释就比如我们水龙头放水,阀门一打开,水哗哗的往下流,秉着勤俭节约的优 良传统美德,我们要把水龙头关小点,最好是如我们心意按照一定规律在某个时间间隔内 一滴一滴的往下滴
如下,持续触发 scroll 事件时,并不立即执行 handle 函数,每隔 1000 毫秒才会执行一次 handle 函数
var throttle =function(func, delay) {
var prev = Date.now(); return function() {
var context = this;
var args = arguments; var now = Date.now();
if (now - prev >= delay) { func.apply(context, args); prev = Date.now();
}
} }
function handle() {console.log(Math.random());} window.addEventListener('scroll', throttle(handle, 1000));
总结:
函数防抖:将几次操作合并为一此操作进行。原理是维护一个计时器,规定在 delay 时间后 触发函数,但是在 delay 时间内再次触发的话,就会取消之前的计时器而重新设置。这样一 来,只有最后一次操作能被触发
函数节流:使得一定时间内只触发一次函数。原理是通过判断是否到达一定时间来触发函 数
区别:
函数节流不管事件触发有多频繁,都会保证在规定时间内一定会执行一次真正的事件处理 函数,而函数防抖只是在最后一次事件后才触发一次函数。比如在页面的无限加载场景下, 我们需要用户在滚动页面时,每隔一段时间发一次Ajax 请求,而不是在用户停下滚动页面操作时才去请求数据。这样的场景,就适合用节流 技术来实现
28、如何判断 JavaScript 的数据类型?
JavaScript 数据类型一共有 7 种:
Undefined、Null、Boolean、String、Symbol、Number、Object
除了 Object 之外的 6 种属于原始数据类型。有时,我们还会细分 Object 的类型,比如 Array, Function,Date,RegExp 等
判断方法
1、typeof
typeof 可以用来区分除了 Null 类型以外的原始数据类型,对象类型的可以从普通对象里面 识别出函数:
typeof undefined // "undefined" typeof null // "object"
typeof 1 // "number"
typeof "1" // "string"
typeof Symbol() // "symbol" typeof function() {} // "function" typeof {} // "object"
问题一:typeof 不能识别 null,如何识别 null?
答案:如果想要判断是否为 null,可以直接使用===全等运算符来判断(或者使用下面的 Object.prototype.toString 方法):
let a = null
a === null // true
问题二:typeof 作用于未定义的变量,会报错吗? 答案:不会报错,返回"undefined"。
问题三:typeof Number(1)的返回值是什么?
答案:“number”。注意 Number 和 String 作为普通函数调用的时候,是把参数转化为相 应 的原始数据类型,也就是类似于做一个强制类型转换的操作,而不是默认当做构造函数 调 用。注意和 Array 区分,Array(…)等价于 new Array(…)
typeof Number(1) // "number" typeof String("1") // "string" Array(1, 2, 3)
// 等价于
new Array(1, 2, 3)
2、instanceof
instanceof 不能用于判断原始数据类型的数据:
3 instanceof Number // false '3' instanceof String // false true instanceof Boolean // false
instanceof 可以用来判断对象的类型:
var date = new Date()
date instanceof Date // true
var number = new Number() number instanceof Number // true var string = new String()
string instanceof String // true
需要注意的是,instanceof 的结果并不一定是可靠的,因为在 ECMAScript7 规范中可以通 过自定义 Symbol.hasInstance 方法来覆盖默认行为。
3、Object.prototype.toString
Object.prototype.toString.call(undefined).slice(8, -1) // "Undefined"
Object.prototype.toString.call(null).slice(8, -1) // "Null"
Object.prototype.toString.call(3).slice(8, -1) // "Number"
Object.prototype.toString.call(new Number(3)).slice(8, -1)//"Number"
Object.prototype.toString.call(true).slice(8, -1)//"Boolean"
Object.prototype.toString.call('3').slice(8, -1) //"String"
Object.prototype.toString.call(Symbol()).slice(8, -1) //"Symbol"
4、Array.isArray
Array.isArray(value)可以用来判断 value 是否是数组:
Array.isArray([]) // true
Array.isArray({}) // false
(function () {console.log(Array.isArray(arguments))}()) // false
29、创建对象有几种方法
1、字面量对象 // 默认这个对象的原型链指向 object
var o1 = {name: ‘01’};
2、通过 new Object 声明一个对象
var o11 = new Object({name: ‘011’});
3、使用显式的构造函数创建对象
var M = function(){this.name=‘o2’};
var o2 = new M();
o2.proto=== M.prototype
o2 的构造函数是 M
o2 这个普通函数,是 M 这个构造函数的实例
4、object.create()
var P = {name:'o3'};
var o3 = Object.create(P);
30、=== 和 ==的区别?
区别:
===: 三个等号我们称为等同符,当等号两边的值为相同类型的时候,直接比较等号两边 的值,值相同则返回 true,若等号两边的值类型不同时直接返回 false。也就是说三个等号 既要判断值也要判断类型是否相等
==:两个等号我们称为等值符,当等号两边的值为相同类型时比较值是否相同,类型不同 时会发生类型的自动转换,转换为相同的类型后再作比较。也就是说两个等号只要值相等就可以。
写给看到最后的你
亲爱的朋友,感谢你看到了最后,如果有技术不成熟的地方请多多指点,感谢!如果你觉得不错,可以点赞+评论+关注任选哦,比心❤️❤️❤️