资讯专栏INFORMATION COLUMN

温故js系列(1)-基本数据类型和引用数据类型判断&存储访问&类型转换

jone5679 / 1529人阅读

摘要:引用数据类型引用数据类型值指保存在堆内存中的对象。访问方式是按引用访问。数据类型检测操作符是检测基本类型的最佳工具。未定义布尔值字符串数值对象或函数用于检测引用类型,可以检测到它是什么类型的实例。

前端学习:教程&开发模块化/规范化/工程化/优化&工具/调试&值得关注的博客/Git&面试-前端资源汇总

欢迎提issues斧正:数据类型

回味,无穷!

数据类型定义 数据类型分类

基本数据类型:String,boolean,Number,Symbol(ES6新增),Undefined, Null
引用数据类型:Object
基本数据类型中有两个为特殊数据类型: null, undefined
js的常见内置对象:Date,Array,Math,Number,Boolean,String,Array,RegExp,Function...

数据类型访问&&复制

基本数据类型:基本数据类型值指保存在栈内存中的简单数据段。访问方式是按值访问。

var a = 1;

操作的是变量实际保存的值。

a = 2;

基本类型变量的复制:从一个变量向一个变量复制时,会在栈中创建一个新值,然后把值复制到为新变量分配的位置上。

var b = a;

b = 2;

引用数据类型:引用数据类型值指保存在堆内存中的对象。也就是,变量中保存的实际上的只是一个指针,这个指针指向内存中的另一个位置,该位置保存着对象。访问方式是按引用访问。

var a = new Object();

当操作时,需要先从栈中读取内存地址,然后再延指针找到保存在堆内存中的值再操作。

a.name = "xz";

引用类型变量的复制:复制的是存储在栈中的指针,将指针复制到栈中未新变量分配的空间中,而这个指针副本和原指针指向存储在堆中的同一个对象;复制操作结束后,两个变量实际上将引用同一个对象。因此,在使用时,改变其中的一个变量的值,将影响另一个变量。

var b = a;

b.sex = "boy";

漏画了,差一条指针。b的引用指针也指向object{sex:"boy"}

b.sex;  //"boy"   a.name; //"boy"
堆&栈

两者都是存放临时数据的地方。
栈是先进后出的,就像一个桶,后进去的先出来,它下面本来有的东西要等其他出来之后才能出来。
堆是在程序运行时,而不是在程序编译时,申请某个大小的内存空间。即动态分配内存,对其访问和对一般内存的访问没有区别。对于堆,我们可以随心所欲的进行增加变量和删除变量,不用遵循次序。
栈区(stack) 由编译器自动分配释放 ,存放函数的参数值,局部变量的值等。
堆区(heap) 一般由程序员分配释放,若程序员不释放,程序结束时可能由OS回收。
堆(数据结构):堆可以被看成是一棵树,如:堆排序;
栈(数据结构):一种先进后出的数据结构。

数据类型检测 Typeof

typeof操作符是检测基本类型的最佳工具。

"undefined" — 未定义
"boolean"   — 布尔值
"string"    — 字符串
"number"    — 数值
"object"    — 对象或null
"function"  — 函数
Instanceof

instanceof用于检测引用类型,可以检测到它是什么类型的实例。
instanceof 检测一个对象A是不是另一个对象B的实例的原理是:查看对象B的prototype指向的对象是否在对象A的[[prototype]]链上。如果在,则返回true,如果不在则返回false。不过有一个特殊的情况,当对象B的prototype为null将会报错(类似于空指针异常)。

var sXzaver = new String("Xzavier"); 
console.log(sXzaver instanceof String);   //  "true"
var aXzaver = [1,2,3]; 
console.log(aXzaver instanceof Array);   //  "true"
检测数组在ECMA Script5中定义了一个新方法Array.isArray()
Constructor

constructor属性返回对创建此对象的数组函数的引用。可以用于检测自定义类型。

"xz".constructor == String // true
(123).constructor == Number // true
(true).constructor == Boolean // true
[1,2].constructor == Array // true
({name:"xz"}).constructor == Object // true
(function(){}).constructor == Function // true
(new Date()).constructor == Date // true
(Symbol()).constructor == Symbol // true
(/xz/).constructor == RegExp // true

constructor不适用于null和undefined。除了这些原生的,constructor还可验证自定义类型。

function Xzavier(){}
var xz = new Xzavier();
xz.constructor == Xzavier;  // true 
Object.prototype.toString.call(obj)

推荐使用:Object.prototype.toString.call(obj)

原理:调用从Object继承来的原始的toString()方法

Object.prototype.toString.call("xz"); //"[object String]"
Object.prototype.toString.call(123);  //"[object Number]"
Object.prototype.toString.call(true); //"[object Boolean]"
Object.prototype.toString.call([1,2]); //"[object Array]"
Object.prototype.toString.call({name:"xz"}); //"[object Object]"
Object.prototype.toString.call(function(){}); //"[object Function]"
Object.prototype.toString.call(null); //"[object Null]"
Object.prototype.toString.call(undefined); //"[object Undefined]"
Object.prototype.toString.call(); //"[object Undefined]"
Object.prototype.toString.call(new Date()); //"[object Date]"
Object.prototype.toString.call(/xz/);  //"[object RegExp]"
Object.prototype.toString.call(Symbol()); //"[object Symbol]"

var obj = {name:"Xzavier", age:23};
var a = [1,2,3];

function isType(obj) {
    return Object.prototype.toString.call(obj).slice(8, -1);
}
isType(obj);  // "Object" 
isType(a)  // "Array"  
数据类型转换 隐式转换
undefined == null;  // true   
1 == true;  // true  
2 == true;  // false  
0 == false;  // true
0 == "";  // true   
NaN == NaN;  // false  NaN不等于任何值
[] == false;  // true  
[] == ![];  // true
"6" - "3"  // 3
1234 + "abcd" // "1234abcd"

1.undefined与null相等,但不恒等(===)
2.一个是number一个是string时,会尝试将string转换为number
3.隐式转换将boolean转换为number,0或1
4.隐式转换将Object转换成number或string,取决于另外一个对比量的类型
5.对于0、空字符串的判断,建议使用 “===” 。
6.“==”会对不同类型值进行类型转换再判断,“===”则不会。它会先判断两边的值类型,类型不匹配时直接为false。

显示转换

显示转换一般指使用Number、String和Boolean三个构造函数,手动将各种类型的值,转换成数字、字符串或者布尔值。

Number:
Number("1234") // 1234
Number("1234abcd") // NaN
Number("") // 0
Number(true) // 1
Number(null) // 0
Number(undefined) // NaN
String:
String(1234)  // "1234"
String("abcd")  // "abcd"
String(true)  // "true"
String(undefined) // "undefined"
String(null)  // "null"
Boolean:
Boolean(0)  // false
Boolean(undefined)  // false
Boolean(null)  // false
Boolean(NaN)  // false
Boolean("")  // false

使用总,!!相当于Boolean:

!!"foo";   // true
!!"";      // false
!!"0";     // true
!!"1";     // true
!!"-1"     // true
!!{};      // true
!!true;    // true

Number、String、Boolean转换对象时主要使用了对象内部的valueOf和toString方法进行转换。

Number转换对象:

1.先调用对象自身的valueOf方法。如果返回原始类型的值,则直接对该值使用Number函数,返回结果。
2.如果valueOf返回的还是对象,继续调用对象自身的toString方法。如果toString返回原始类型的值,则对该值使用Number函数,返回结果。
3.如果toString返回的还是对象,报错。

Number([1]); //1
转换演变:
[1].valueOf(); // [1];
[1].toString(); // "1";
Number("1"); //1
String转换对象

1.先调用对象自身的toString方法。如果返回原始类型的值,则对该值使用String函数,返回结果。
2.如果toString返回的是对象,继续调用valueOf方法。如果valueOf返回原始类型的值,则对该值使用String函数,返回结果。
3.如果valueOf返回的还是对象,报错。

String([1,2]) //"1,2"
转化演变:
[1,2].toString();  //"1,2"
String("1,2");  //"1,2"
Boolean转换对象

Boolean转换对象很特别,除了以下六个值转换为false,其他都为true

undefined  null  false  0(包括+0和-0)  NaN  空字符串("")
Boolean(undefined)   //false
Boolean(null)        //false
Boolean(false)       //false
Boolean(0)           //false
Boolean(NaN)         //false
Boolean("")          //false

Boolean([])          //true
Boolean({})          //true
Boolean(new Date())  //true

写写博客打打球...要代码,要篮球,更要生活。。。

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/79870.html

相关文章

  • 温故js系列(9)-相等==&严格相等===&代码里的那些判断

    摘要:业务越复杂,逻辑就越复杂,判断就越多比较判断比较判断是比较两个值,返回一个布尔值,表示是否满足比较条件。对于非布尔值的数据,取反运算符会自动将其转为布尔值。 前端学习:教程&开发模块化/规范化/工程化/优化&工具/调试&值得关注的博客/Git&面试-前端资源汇总 欢迎提issues斧正:========== JavaScript-判断 代码中,多多少少会有判断语句。业务越复杂,逻辑就越...

    libin19890520 评论0 收藏0
  • 温故js系列18)-对象&对象使用

    摘要:对象创建字面量方式构造函数方式也可以这样不过这样的话,为何不选择字面量方式字面量方式和方式的写法是等价的,返回的结果是同种类的对象。构造函数产生实例时,实例通过其对应原型对象的访问对应的构造函数对象。 前端学习:教程&模块化/规范化/工程化/优化&工具/调试&值得关注的博客/Git&面试资源汇总 欢迎提issues斧正:对象&对象使用 Object对象 在 JavaScript 中,对...

    keke 评论0 收藏0
  • 温故js系列12)-ajax&&优缺点&&node后端

    摘要:接收响应当请求发送到服务器端,收到响应后,响应的数据会自动填充对象的属性。一般而已状态代码为作为成功的标志。必要时,可以将查询字符串参数追加到的末尾,以便提交给服务器。后端实现可以自学一点后端知识,便于学习。 前端学习:教程&开发模块化/规范化/工程化/优化&工具/调试&值得关注的博客/Git&面试-前端资源汇总 欢迎提issues斧正:Ajax JavaScript-Ajax&&no...

    LiangJ 评论0 收藏0
  • 温故js系列14)-闭包&垃圾回收&内存泄露&闭包应用&作用域链&

    摘要:该对象包含了函数的所有局部变量命名参数参数集合以及,然后此对象会被推入作用域链的前端。如果整个作用域链上都无法找到,则返回。此时的作用域链包含了两个对象的活动对象和对象。 前端学习:教程&开发模块化/规范化/工程化/优化&工具/调试&值得关注的博客/Git&面试-前端资源汇总 欢迎提issues斧正:闭包 JavaScript-闭包 闭包(closure)是一个让人又爱又恨的somet...

    Amio 评论0 收藏0
  • 温故js系列16)-数组&数组方法使用详解

    摘要:创建数组数组字面量数组构造函数参数为数组建议使用数组字面量方式,性能好,代码少,简洁,毕竟代码少。数组判断方法用来判断某个值是否为。的这是最简洁最直接的遍历数组元素的语法。把数组转换为本地数组,并返回结果。 前端学习:前端教程&开发模块化/规范化/工程化/优化&工具/调试&值得关注的博客/Git&面试-前端资源汇总 欢迎提issues斧正:数组&数组方法使用详解 Array对象 之前一...

    morgan 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<