前端JavaScript的一些面试题

1、JavaScript 的基本类型有哪些?引用类型有哪些?

数据类型 基本数据类型:number、string、boolean、null、undefined

引用数据类型:function、object、Array

2、创建对象有几种方法

创建方法
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)

3、简述创建函数的几种方式?

第一种(函数声明):
function sum1(num1,num2){ 
return num1+num2; 
}
第二种(函数表达式)
var sum2 = function(num1,num2){ 
return num1+num2; 
}
第三种(函数对象方式)
var sum3 = new Function("num1","num2","return num1+num2");

4、Javascript 创建对象的几种方式?

1、简单对象的创建 使用对象字面量的方式{} 创建一个对象(最简单,好理解,推荐使用)

2、用 function(函数)来模拟 class

3、使用工厂方式来创建(Object 关键字)

4、使用原型对象的方式 prototype 关键字

5、混合模式(原型和构造函数)

6、动态原型的方式(可以看作是混合模式的一种特例)

5、JavaScript 内置的常用对象有哪些?

1、Array 数组 

2、Date 日期时间

3、Error 异常对象

4、Math 数学对象

5、Number 数值对象

6、Object 基础对象

7、RegExp 正则表达式对象

8、String 字符串对象

6、如何区分数组和对象?

方法一:通过 ES6 中的 Array.isArray 来识别

方法二:通过 instanceof 来识别

方法三:通过调用 constructor 来识别

方法四:通过 Object.prototype.toString.call 方法来识别

7、怎么判断两个对象相等?

想要比较两个对象内容是否一致,思路是要遍历对象的所有键名和键值是否都一致:

1、判断两个对象是否指向同一内存

2、使用 Object.getOwnPropertyNames 获取对象所有键名数组

3、判断两个对象的键名数组是否相等

4、遍历键名,判断键值是否都相等

8、列举三种强制类型转换和两种隐式类型转换?

强制

转化成字符串 toString() String()

转换成数字 Number()、 parseInt()、 parseFloat()

转换成布尔类型 Boolean()

隐式

拼接字符串     例子 var str = "" + 18     

- * / % ==

9、JavaScript 中的作用域、预解析与变量声明提升?

作用域

就是变量的有效范围。 在一定的空间里可以对数据进行读写操作,这个空间就是数据的 作用域 1、全局作用域: 最外层函数定义的变量拥有全局作用域,即对任何内部函数来说,都是可以访问的;

2、局部作用域: 局部作用域一般只在固定的代码片段内可访问到,而对于函数外部是无 法访问的,最常见的例如函数内部。在 ES6 之前,只有函数可以划分变量的作用域,所 以 在函数的外面无法访问函数内的变量

3、块级作用域:凡是代码块就可以划分变量的作用域,这种作用域的规则就叫块级作用 域

块级作用域 函数作用域 词法作用域之间的区别:

3.1)块级作用域和函数作用域描述的是,什么东西可以划分变量的作用域

3.2)词法作用域描述的是,变量的查找规则

之间的关系:

1、 块级作用域 包含 函数作用域

2、 词法作用域 与 块级作用域、函数作用域之间没有任何交集, 他们从两个角度描 述了作用域的规则

ES6 之前 JavaScript 采用的是函数作用域+词法作用域,ES6 js 采用的是块级作用域+词 法作用域

预解析

JavaScript 代码的执行是由浏览器中的 JavaScript 解析器来执行的。JavaScript 解析器执行 JavaScript 代码的时候,分为两个过程:预解析过程和代码执行过程

预解析过程:

1.把变量的声明提升到当前作用域的最前面,只会提升声明,不会提升赋值

2.把函数的声明提升到当前作用域的最前面,只会提升声明,不会提升调用

变量提升

变量提升:定义变量的时候,变量的声明会被提升到作用域的最上面,变量的赋值不会提 升

函数提升:JavaScript 解析器首先会把当前作用域的函数声明提前到整个作用域的最前面

变量声明提升:

使用 var 关键字定义的变量,被称为变量声明; 函数声明提升的特点是,在函数声明的前面,可以调用这个函数

10、什么是作用域链?

作用域链

当代码在一个环境中执行时,会创建变量对象的一个作用域链

由子级作用域返回父级作用域中寻找变量,就叫做作用域链

作用域链中的下一个变量对象来自包含环境,也叫外部环境。而再下一个变量对象则来自 下一个包含环境,一直延续到全局执行环境。全局执行环境的变量对象始终都是作用域链 中的最后一个对象

作用域链前端始终都是当前执行的代码所在环境的变量对象,如果环境是函数,则将其活 动对象作为变量对象

11、如何延长作用域链?

作用域链是可以延长的

延长作用域链:

执行环境的类型只有两种,全局和局部(函数)。但是有些语句可以在作用域链的前端临 时增加一个变量对象,该变量对象会在代码执行后被移除

具体来说就是执行这两个语句时,作用域链都会得到加强

1、try - catch 语句的 catch 块;会创建一个新的变量对象,包含的是被抛出的错误对象 的声明 2、with 语句。with 语句会将指定的对象添加到作用域链中

12、判断一个值是什么类型有哪些方法?

方法

1、typeof 运算符

2、instanceof 运算符

3、Object.prototype.toString 方法

13、JavaScript 变量按照存储方式区分为哪些类型,并描述 其特点?

1、值类型和引用类型

2、值类型存储的是值 ,赋值之后原变量的值不改变

3、引用类型存储的是地址 ,赋值之后是把原变量的引用地址赋值给新变量 ,新变量改 变 原来的会跟着改变

14、根据你的理解,请简述 JavaScript 脚本的执行原理

原理

JavaScript 是一种动态、弱类型、基于原型的语言,通过浏览器可以直接执行 当浏览器遇到

当浏览器遇到\<script>标记的时候,浏览器会执行之间的 javascript 代码。嵌入的 JavaScript代 码是顺序执行的,每个脚本定义的全局变量和函数,都可以被后面执行的脚本所调用。

变量的调用,必须是前面已经声明,否则获取的变量值是 undefined

15、什么是闭包?

“闭包就是能够读取其他函数内部变量的函数。例如在 javascript 中,只有函数内部的子 函数才能读取局部变量,所以闭包可以理解成“定义在一个函数内部的函数“。在本质上,闭 包是将函数内部和函数外部连接起来的桥梁。”

16、什么是内存泄漏?

内存泄漏指任何对象在您不再拥有或需要它之后仍然存在

17、哪些操作会造成内存泄漏?

1、垃圾回收器定期扫描对象,并计算引用了每个对象的其他对象的数量。如果一个对象 的引用数量为 0(没有其他对象引用过该对象),或对该对象的唯一引用是循环的,那么该对 象的内存即可回收

2、setTimeout 的第一个参数使用字符串而非函数的话,会引发内存泄漏

3、闭包、控制台日志、循环(在两个对象彼此引用且彼此保留时,就会产生一个循环)

18、JS 内存泄漏的解决方式

1、global variables:对未声明的变量的引用在全局对象内创建一个新变量。在浏览器中,全局对象就是 window。

1.1)解决:

1.1.1)创建意外的全局变量

1.1.2)可以在 JavaScript 文件开头添加 “use strict”,使用严格模式。这样在严格模 式下解析 JavaScript 可以防止意外的全局变量

1.1.3)在使用完之后,对其赋值为 null 或者重新分配

1.2)被忘记的 Timers 或者 callbacks

在 JavaScript 中使用 setInterval 非常常见 大多数库都会提供观察者或者其它工具来处理回调函数,在他们自己的实例变为不可达 时,会让回调函数也变为不可达的。

1.3)闭包:一个可以访问外部(封闭)函数变量的内部函数

JavaScript 开发的一个关键方面就是闭包:一个可以访问外部(封闭)函数变量的内部函数

1.4)DOM 引用

有时候,在数据结构中存储 DOM 结构是有用的。假设要快速更新表中的几行内容。将每行 DOM 的引用存储在字典或数组中可能是有意义的。当这种情况发生时,就会保留同一 DOM 元素的 两份引用:一个在 DOM 树种,另一个在字典中。如果将来某个时候你决定要删除这些行,则需要让两个引用都不可达。

19、说说你对原型(prototype)理解

JavaScript 是一种通过原型实现继承的语言与别的高级语言是有区别的,像 java,C#是通 过类型决定继承关系的,JavaScript 是的动态的弱类型语言,总之可以认为 JavaScript 中所 有都是对象,在 JavaScript 中,原型也是一个对象,通过原型可以实现对象的属性继承, JavaScript 的对象中都包含了一个” prototype”内部属性,这个属性所对应的就是该对象 的原型

“prototype”作为对象的内部属性,是不能被直接访问的。所以为了方便查看一个对象 的原型,Firefox 和 Chrome 内核的 JavaScript 引擎中提供了”proto“这个非标准的访问器 (ECMA 新标准中引入了标准对象原型访问器”Object.getPrototype(object)”) 原型的主要作用就是为了实现继承与扩展对象

20、介绍下原型链(解决的是继承问题吗)

JavaScript 原型: 每个对象都会在其内部初始化一个属性,就是 prototype(原型)

原型链:

当我们访问一个对象的属性时,如果这个对象内部不存在这个属性,那么他就会去 prototype 里找这个属性,这个 prototype 又会有自己的 prototype,于是就这样一直找 下去,也就是我们平时所说的原型链的概念

特点:

JavaScript 对象是通过引用来传递的,我们创建的每个新对象实体中并没有一份属于自己 的原型副本。当我们修改原型时,与之相关的对象也会继承这一改变

21、常见的 js 中的继承方法有哪些

继承有以下六种方法

1、原型链继承 JavaScript 实现继承的基本思想:通过原型将一个引用类型继承另一个引 用 类型的属性和方法

2、借用构造函数继承(伪造对象或经典继承) JavaScript 实现继承的基本思想:在子类构造 函数内部调用超类型构造函数。 通过使用 apply()和 call()方法可以在新创建的子类对象上 执 行构造函数

3、组合继承(原型+借用构造)(伪经典继承) JavaScript 实现继承的基本思想:将原型链和借 用构造函数的技术组合在一块,从而发挥两者之长的一种继承模式 将原型链和借用构造函数的技术组合到一起,从而取长补短发挥两者长处的一种继承模式

4、型式继承 JavaScript 实现继承的基本思想:借助原型可以基于已有的对象创建新对 象,同时还不必须因此创建自定义的类型

5、寄生式继承 JavaScript 实现继承的基本思想:创建一个仅用于封装继承过程的函数, 该 函数在内部以某种方式来增强对象,最后再像真正是它做了所有工作一样返回对象。 寄生式继承是原型式继承的加强版

6、寄生组合式继承 JavaScript 实现继承的基本思想:通过借用函数来继承属性,通过原 型 链的混成形式来继承方法

22、介绍 this 各种情况

1、以函数形式调用时,this 永远都是 window

2、以方法的形式调用时,this 是调用方法的对象

3、以构造函数的形式调用时,this 是新创建的那个对象

4、使用 call 和 apply 调用时,this 是指定的那个对象

5、箭头函数:箭头函数的 this 看外层是否有函数 如果有,外层函数的 this 就是内部箭头函数的 this 如果没有,就是 window

6、特殊情况:通常意义上 this 指针指向为最后调用它的对象。这里需要注意的一点就是 如果返回值是一个对象,那么 this 指向的就是那个返回的对象,如果返回值不是一个对象那么 this 还是指向函数的实例

23、谈谈你对 Javascript 垃圾回收机制的理解?

1、标记清除(mark and sweep)

这是 JavaScript 最常见的垃圾回收方式,当变量进入执行环境的时候,比如函数中声明一个变 量,垃圾回收器将其标记为“进入环境”,当变量离开环境的时候(函数执行结束)将其标记 为“离开环境”

垃圾回收器会在运行的时候给存储在内存中的所有变量加上标记,然后去掉环境中的变量以及 被环境中变量所引用的变量(闭包),在这些完成之后仍存在标记的就是要删除的变量了

2、引用计数(reference counting)

在低版本 IE 中经常会出现内存泄露,很多时候就是因为其采用引用计数方式进行垃圾回收。引 用计数的策略是跟踪记录每个值被使用的次数,当声明了一个 变量并将一个引用类型赋值给该 变量的时候这个值的引用次数就加 1,如果该变量的值变成了另外一个,则这个值得引用次数 减 1,当这个值的引用次数变为 0 的时 候,说明没有变量在使用,这个值没法被访问了,因此 可以将其占用的空间回收,这样垃圾回收器会在运行的时候清理掉引用次数为 0 的值占用的空 间

在 IE 中虽然 JavaScript 对象通过标记清除的方式进行垃圾回收,但 BOM 与 DOM 对象却是通过 引用计数回收垃圾的,也就是说只要涉及 BOM 及 DOM 就会出现循环引用问题

24、什么是 js 事件循环 event loop

主线程从"任务队列"中读取事件,这个过程是循环不断的,所以整个的这种运行机制又称 为 Event Loop(事件循环)

25、JS 里垃圾回收机制是什么,常用的是哪种,怎么处理的?

JS 的垃圾回收机制是为了以防内存泄漏,内存泄漏的含义就是当已经不需要某块内存 时这块内存还存在着,垃圾回收机制就是间歇的不定期的寻找到不再使用的变量,并释放 掉它们所指向的内存

JS 中最常见的垃圾回收方式是标记清除

工作原理:是当变量进入环境时,将这个变量标记为“进入环境”。当变量离开环境时, 则将其标记为“离开环境”。标记“离开环境”的就回收内存

工作流程:

垃圾回收器,在运行的时候会给存储在内存中的所有变量都加上标记 去掉环境中的变量以及被环境中的变量引用的变量的标记 再被加上标记的会被视为准备删除的变量 垃圾回收器完成内存清除工作,销毁那些带标记的值并回收他们所占用的内存空间

26、栈和队列的区别?

1、栈的插入和删除操作都是在一端进行的,而队列的操作却是在两端进行的

2、队列先进先出,栈先进后出

3、栈只允许在表尾一端进行插入和删除,而队列只允许在表尾一端进行插入,在表头一 端进行删除#

27、栈和堆的区别?

1、栈区(stack)— 由编译器自动分配释放 ,存放函数的参数值,局部变量的值等。 堆区(heap) — 一般由程序员分配释放, 若程序员不释放,程序结束时可能由 OS 回收

2、堆(数据结构):堆可以被看成是一棵树,如:堆排序; 栈(数据结构):一种先进 后出的数据结构

  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值