今天,来说几道比较经典的高频前端面试题,话不多说,直奔主题。
let、const、var的区别
一、var声明的变量会挂载在window上,而let和const声明的变量不会。
console.log(a,window.a);
let b = 2;
console.log(b,window.b);
const c = 3;
console.log(c,window.c);
二、var声明变量存在变量提升,let和const不存在变量提升。
console.log(a);
var a = 1;
console.log(b);
let b = 1;
console.log(c);
const c = 1;
三、let和const声明形成块作用域。
if(1){
var a = 100;
let b = 10
}
function fn(){
return {
a:100
}
}
fn()
console.log(a);
console.log(b)
四、同一作用域下let和const不能声明同名变量,而var可以。
const a = 1;
const a = 4;
console.log(a);
暂时死区:
if(1){
a = 10;
在当前块作用域中存在a使用let/const声明的情况下,给a赋值10时,只会在当前作用域找变量a,
而这时,还未到声明时候,所以控制台Error:a is not defined
let a = 1;
console.log(a)
let a = 1;
}
const:
* 1、一旦声明必须赋值。
* 2、声明后不能再修改。
* 3、如果声明的是复合类型数据,可以修改其属性
const a = 1;
a = 3
没有修改指针,只是修改了堆内存中的属性,所以允许被修改
const list = [];
list[0] = 10;
console.log(list); // [10]
const obj = {a:100};
obj.name = 'apple';
obj.a = 10000;
console.log(obj); // {a:10000,name:'apple'}
obj = {b:200} // 修改了复合数据类型的指针,导致报错
闭包
闭包说的通俗一点就是可以在函数外部访问到函数内部的变量。因为正常情况下函数外部是访问不到函数内部作用域变量的,作用域分为了全局、函数级、块级作用。
表象判断是不是闭包:函数嵌套函数,内部函数被 return 内部函数调用外层函数的局部变量。
let obj = {
name:'哈哈哈',
fn:function(){
return this.name
}
}
obj.fn();
// 释放obj的内存
obj = null;
优点:可以隔离作用域,不造成全局污染,可以让垃圾回收机制不会回收这个变量,让他能一直被标记为被引用。
缺点:由于闭包长期驻留内存,则会导致大量内存永远不会被释放。
如何释放内存:将暴露外部的闭包变量置为 null。
箭头函数里面的 this 指向是什么样子的?
箭头函数和普通函数的区别是:箭头函数指向定义时,定义的时候 this 就确定了,指向它的外层。 普通函数是指向调用时.谁调用的我.this 就指向的谁。
箭头函数的特点
1、没有构造函数,不能new实例对象
2、本身没有this指向,this指向父级
3、不能使用argumetns
4、没有原型
// 箭头函数使表达更加简洁,隐式返回值
// 正常的写法
const isEven = function(n){
return n % 2 === 0;
}
const square = function(n){
return n * n;
}
const isEven = n => n % 2 === 0;
const square = n => n * n;
// 箭头函数的一个用处是简化回调函数
// 正常函数写法
[1,2,3].map(function (x) {
return x * x;
});
// 箭头函数写法
[1,2,3].map(x => x * x); //[1,4,9]
每个字符串出现的次数
let obj={}
// 将这个字符串放入对象中,进行遍历
for(let i=0;i<str.length;i++){
// 判断字符串的每一个是否存在
if(obj[str[i]]){
// 如果存在就++
obj[str[i]=++obj[str[i]]]
}else{
// 不存在就等于1
obj[str[i]]=1
}
}
// 最后输出结果
console.log(obj);
今天就写到这里,留个赞吧。