网站首页 > 技术文章 正文
JS数据类型
JS基本有5种简单数据类型:String,Number,Boolean,Null,Undefined。引用数据类型:Object,Array,Function。
判断数据类型的方法
在写业务逻辑的时候,经常要用到JS数据类型的判断,面试常见的案例深浅拷贝也要用到数据类型的判断。
typeof
console.log(typeof 2); // number console.log(typeof true); // boolean console.log(typeof 'str'); // string console.log(typeof undefined); // undefined console.log(typeof []); // object console.log(typeof {}); // object console.log(typeof function(){}); // function console.log(typeof null); // object 复制代码
优点:能够快速区分基本数据类型 缺点:不能将Object、Array和Null区分,都返回object
instanceof
console.log(2 instanceof Number); // false console.log(true instanceof Boolean); // false console.log('str' instanceof String); // false console.log([] instanceof Array); // true console.log(function(){} instanceof Function); // true console.log({} instanceof Object); // true 复制代码
优点:能够区分Array、Object和Function,适合用于判断自定义的类实例对象 缺点:Number,Boolean,String基本数据类型不能判断
Object.prototype.toString.call()
var toString = Object.prototype.toString; console.log(toString.call(2)); //[object Number] console.log(toString.call(true)); //[object Boolean] console.log(toString.call('str')); //[object String] console.log(toString.call([])); //[object Array] console.log(toString.call(function(){})); //[object Function] console.log(toString.call({})); //[object Object] console.log(toString.call(undefined)); //[object Undefined] console.log(toString.call(null)); //[object Null] 复制代码
优点:精准判断数据类型 缺点:写法繁琐不容易记,推荐进行封装后使用
var,let,const的区别
let 为 ES6 新添加申明变量的命令,它类似于 var,但是有以下不同:
- var 声明的变量,其作用域为该语句所在的函数内,且存在变量提升现象
- let 声明的变量,其作用域为该语句所在的代码块内,不存在变量提升
- const声明的变量不允许修改
null和undefined区别
Undefined类型只有一个值,即undefined。当声明的变量还未被初始化时,变量的默认值为undefined。用法:
- 变量被声明了,但没有赋值时,就等于undefined。
- 调用函数时,应该提供的参数没有提供,该参数等于undefined。
- 对象没有赋值的属性,该属性的值为undefined。
- 函数没有返回值时,默认返回undefined。
Null类型也只有一个值,即null。null用来表示尚未存在的对象,常用来表示函数企图返回一个不存在的对象。用法
- 作为函数的参数,表示该函数的参数不是对象。
- 作为对象原型链的终点。
定义函数的方法
- 函数声明
//ES5 function getSum(){} function (){}//匿名函数 //ES6 ()=>{} 复制代码
- 函数表达式
//ES5 var getSum=function(){} //ES6 let getSum=()=>{} 复制代码
- 构造函数
const getSum = new Function('a', 'b' , 'return a + b') 复制代码
JS作用域的理解
JS中的作用域分为两种:全局作用域和函数作用域。函数作用域中定义的变量,只能在函数中调用,外界无法访问。没有块级作用域导致了if或for这样的逻辑语句中定义的变量可以被外界访问,因此ES6中新增了let和const命令来进行块级作用域的声明。
更多作用域的了解可以看JS作用域
闭包的理解
简单来说闭包就是在函数里面声明函数,本质上说就是在函数内部和函数外部搭建起一座桥梁,使得子函数可以访问父函数中所有的局部变量,但是反之不可以,这只是闭包的作用之一,另一个作用,则是保护变量不受外界污染,使其一直存在内存中,在工作中我们还是少使用闭包的好,因为闭包太消耗内存,不到万不得已的时候尽量不使用。
更多闭包的内容可以看JS闭包
数组去重
let arr = [1,'1',2,'2',1,2,'x','y','f','x','y','f']; function unique1(arr){ let result = [arr[0]]; for (let i = 1; i < arr.length; i++) { let item = arr[i]; if(result.indexOf(item) == -1){ result.push(item); } } return result; } console.log(unique1(arr)); 复制代码
更多JS去重的方法JS数组去重
call,apply和bind区别
三个函数的作用都是将函数绑定到上下文中,用来改变函数中this的指向;三者的不同点在于语法的不同。
fun.call(thisArg[, arg1[, arg2[, ...]]]) fun.apply(thisArg, [argsArray]) 复制代码
所以apply和call的区别是call方法接受的是若干个参数列表,而apply接收的是一个包含多个参数的数组。
而bind()方法创建一个新的函数, 当被调用时,将其this关键字设置为提供的值,在调用新函数时,在任何提供之前提供一个给定的参数序列。
var bindFn = fun.bind(thisArg[, arg1[, arg2[, ...]]]) bindFn() 复制代码
Demos:
var name = 'window'; var sayName = function (param) { console.log('my name is:' + this.name + ',my param is ' + param) }; //my name is:window,my param is window param sayName('window param') var callObj = { name: 'call' }; //my name is:call,my param is call param sayName.call(callObj, 'call param'); var applyObj = { name: 'apply' }; //my name is:apply,my param is apply param sayName.apply(applyObj, ['apply param']); var bindObj = { name: 'bind' } var bindFn = sayName.bind(bindObj, 'bind param') //my name is:bind,my param is bind param bindFn(); 复制代码
==和===区别
- ==, 两边值类型不同的时候,要先进行类型转换,再比较
- ===,不做类型转换,类型不同的一定不等。
==类型转换过程:
- 如果类型不同,进行类型转换
- 判断比较的是否是 null 或者是 undefined, 如果是, 返回 true .
- 判断两者类型是否为 string 和 number, 如果是, 将字符串转换成 number
- 判断其中一方是否为 boolean, 如果是, 将 boolean 转为 number 再进行判断
- 判断其中一方是否为 object 且另一方为 string、number 或者 symbol , 如果是, 将 object 转为原始类型再进行判断
深拷贝和浅拷贝
浅拷贝
function simpleClone(obj) { var result = {}; for (var i in obj) { result[i] = obj[i]; } return result; } 复制代码
深拷贝,遍历对象中的每一个属性
function deepClone(obj) { let result; if (typeof obj == 'object') { result = isArray(obj) ? [] : {} for (let i in obj) { //isObject(obj[i]) ? deepClone(obj[i]) : obj[i] //多谢"朝歌在掘金"指出,多维数组会有问题 result[i] = isObject(obj[i])||isArray(obj[i])?deepClone(obj[i]):obj[i] } } else { result = obj } return result } function isObject(obj) { return Object.prototype.toString.call(obj) == "[object Object]" } function isArray(obj) { return Object.prototype.toString.call(obj) == "[object Array]" } 复制代码
防抖和节流
防抖
function debounce(fn, delay) { let timer = null; return function () { if (timer) clearTimeout(timer); timer = setTimeout(() => { fn.apply(this, arguments); }, delay); } } 复制代码
节流
function throttle(fn, cycle) { let start = Date.now(); let now; let timer; return function () { now = Date.now(); clearTimeout(timer); if (now - start >= cycle) { fn.apply(this, arguments); start = now; } else { timer = setTimeout(() => { fn.apply(this, arguments); }, cycle); } } } 复制代码
cookie,sessionStorage和localStorage
- cookie用来保存登录信息,大小限制为4KB左右
- localStorage是Html5新增的,用于本地数据存储,保存的数据没有过期时间,一般浏览器大小限制在5MB
- sessionStorage接口方法和localStorage类似,但保存的数据的只会在当前会话中保存下来,页面关闭后会被清空。
名称生命期大小限制与服务器通信cookie一般由服务器生成,可设置失效时间。如果在浏览器端生成Cookie,默认是关闭浏览器后失效4KB每次都会携带在HTTP头中,如果使用cookie保存过多数据会带来性能问题localStorage除非被清除,否则永久保存5MB仅在浏览器中保存,不与服务器通信sessionStorage仅在当前会话下有效,关闭页面或浏览器后被清除5MB仅在浏览器中保存,不与服务器通信
0.1+0.2!=0.3怎么处理
把需要计算的数字升级(乘以10的n次幂)成计算机能够精确识别的整数,等计算完成后再进行降级(除以10的n次幂),即:
(0.1*10 + 0.2*10)/10 == 0.3 //true 复制代码
更多关于浮点数精度处理请看JS中浮点数精度问题
JS实现继承
首先创建一个父类
// 定义一个动物类 function Animal(name, color) { // 属性 this.name = name || 'Animal'; this.color = color || ['black']; // 实例方法 this.sleep = function () { console.log(this.name + '正在睡觉!'); } } // 原型方法 Animal.prototype.eat = function (food) { console.log(this.name + '正在吃:' + food); }; 复制代码
原型链继承
new了一个空对象,这个空对象指向Animal并且Cat.prototype指向了这个空对象,这种就是基于原型链的继承。
function Cat(name) { this.name = name || 'tom' } Cat.prototype = new Animal() var cat = new Cat() cat.color.push('red') cat.sleep() //tom正在睡觉! cat.eat('fish') //tom正在吃:fish console.log(cat.color) //["black", "red"] console.log(cat instanceof Animal) //true console.log(cat instanceof Cat) //true var new_cat = new Cat() console.log(new_cat.color) //["black", "red"] 复制代码
- 特点:基于原型链,既是父类的实例,也是子类的实例。
- 缺点:1.无法实现多继承;2.所有新实例都会共享父类实例的属性。
构造继承
function Dog(name) { Animal.call(this) this.name = name || 'mica' } var dog = new Dog() dog.color.push('blue') dog.sleep() // mica正在睡觉! dog.eat('bone') //Uncaught TypeError: dog.eat is not a function console.log(dog.color) //["black", "blue"] console.log(dog instanceof Animal) //false console.log(dog instanceof Dog) //true var new_dog = new Dog() console.log(new_dog.color) //["black"] 复制代码
- 特点:可以实现多继承(call多个),解决了所有实例共享父类实例属性的问题。
- 缺点:1.只能继承父类实例的属性和方法;2.不能继承原型上的属性和方法。
组合继承
function Mouse(name){ Animal.call(this) this.name = name || 'jerry' } Mouse.prototype = new Animal() Mouse.prototype.constructor = Mouse var mouse = new Mouse() mouse.color.push('yellow) mouse.sleep() //jerry正在睡觉! mouse.eat('carrot') //jerry正在吃:carrot console.log(mouse instanceof Animal)//true console.log(mouse instanceof Mouse)//true var new_mouse = new Mouse() console.log(new_mouse.color) //["black"] 复制代码
- 特点:可以继承实例属性/方法,也可以继承原型属性/方法
- 缺点:调用了两次父类构造函数,生成了两份实例
链接来源:https://juejin.im/post/5df1e312f265da33d039d06d
猜你喜欢
- 2025-06-24 晨光微醺时!2 道 JS 核心题漫谈,解锁面试小技巧
- 2025-06-24 js基础面试题92-130道题目(50道js面试题)
- 2025-06-24 3 个高级 JavaScript 面试问题(js面试题必问)
- 2025-06-24 晨光微暖时!2 道 JS 经典面试题拆解,开启惬意学习日
- 2025-06-24 JS面试题突破:谈谈 undefined 和 null ?
- 2025-06-24 9 个你可能不知道答案的常见 JavaScript 面试题
- 2025-06-24 19个基本的JavaScript面试问题及答案(都是实用技巧)免费送
- 2025-06-24 JavaScript篇面试题(js面试题基础)
- 2024-10-05 前端面试,你有必要知道的一些JavaScript 面试题(上)
- 2024-10-05 几道看起来代码量很少的Javascript笔试题,看看你会不会做?
你 发表评论:
欢迎- 最近发表
- 标签列表
-
- 前端设计模式 (75)
- 前端性能优化 (51)
- 前端模板 (66)
- 前端跨域 (52)
- 前端缓存 (63)
- 前端aes加密 (58)
- 前端脚手架 (56)
- 前端md5加密 (54)
- 前端路由 (61)
- 前端数组 (73)
- 前端js面试题 (50)
- 前端定时器 (59)
- Oracle RAC (76)
- oracle恢复 (77)
- oracle 删除表 (52)
- oracle 用户名 (80)
- oracle 工具 (55)
- oracle 内存 (55)
- oracle 导出表 (62)
- oracle约束 (54)
- oracle 中文 (51)
- oracle链接 (54)
- oracle的函数 (58)
- oracle面试 (55)
- 前端调试 (52)
本文暂时没有评论,来添加一个吧(●'◡'●)