一、toString方法和Object.prototype.toSting.call()的区别

var arr=[1,2];

直接对一个数组调用toString()方法,

console.log(arr.toString());    //输出1,2
现在通过call方法指定arr数组为Object.prototype对象中的toString方法的上下文。
console.log(Object.prototype.toString.call(arr));    //输出[Object Array]
错误理解:按照arr是Object对象的子集,应该toString()方法会继承下来,所以两个得到的结果应该是一样的,但是现实是残酷的。
原因:Object.prototype的toString方法确实被继承下来了,但是很多东西总不会一层不变,作为儿子的数组重写了toString方法,所以直接调用数组对象上面的toString方法调用到的实际是重写后的方法,并不是Object.prototype中的toString方法。Array,Function等类型作为Object的实例,都重写了toString方法,不同的对象类型调用toString()方法时,根据原型链的知识,调用的是重写之后的toString方法(函数返回的是函数体内的字符串,Array返回的是元素组成的字符串)
应用场景:Object.prototype对象上的toString方法可以用来判断数据类型
例如:Object.prototype.toString.call(arr);   输出:[Object Array] 判断是否是数组
 
例子2:
var arr=[1,2,3];
console.log(Array.prototype hasOwnPrototype('toString'))    //true
console.log(arr.toString())   //1,2,3
delete Array.prototype.toString;   //delete操作符可以删除实例属性
console.log(Array.prototype hasOwnPrototype('toString'))    //false
console.log(arr.toString())   //[object Array];
删除了Array的toString方法后,同样采用arr.toString()方法调用,不再屏蔽Object原型方法的实例方法,arr最后调用了Object的toString方法。
 
而重写后的toString方法可以把对象转换成字符串,还可以把数值转换成不同进制的数字
[1,2].toString();//1,2 得到字符串
(10).toString(2)  //十进制转二进制,输出1010,如果10.toString(2)会报错,因为js会认为.是数字的小数点而不是调用符号。
二、为什么用Object.prototype.toString.call(obj)检测对象类型?
第一种:用typeof判断
我们知道typeof可以检测数据类型,对变量或值调用typeof运算符将返回下列值之一:
undefined->Undefined
boolean->Boolean
number->Number
string->String
object->是引用类型或null类型。
function->function函数
typeof检测引用类型或null是不能准确区分arr json等引用类型的。
那我们还知道一种检测方式instanceof,来检测某个对象是不是另一个对爱心那个的实例
第二种:用instanceof判断
instanceof运算符用来测试一个对象在其原型链中是否存在一个构造函数的prototype属性。
主要用来检测引用类型,判断Array和RegExp,无法准确判断Function,因为函数,日期,正则都是对象的特殊形式,所以用instanceof判断Object,都是true.
console.log([] instanceof Array)   //true
console.log({} instanceof Object)   //true
console.log(/\d/ instanceof RegExp)   //true
console.log(function(){} instanceof Object)  //true
console.log(function(){} instanceof Function)   //true
console.log([] instanceof Object)   //true   判断错误
console.log(function(){} instanceof Object)   //true   判断错误
console.log('' instanceof String)   //false
console.log(1 instanceof Number)   //false
 
 
var a=new Array();
alert(a instanceof Array);
同时alert(a instanceof Object)也会返回true,因为Array是object的子类。
function test(){}
var a=new test();
alert(a instanceof test);会返回true.
alert(a==b)  //false;
 
另外,更重要的一点是instanceof可以在继承关系中用来判断一个实例是否属于他的父类型。
function Foo(){}
Foo.prototype=new Aoo()    //js原型继承
var foo= new Foo();
console.log(foo instanceof Foo)   //true
console.log(foo.instanceof Aoo)   //true
上面代码中是判断了一层继承关系的父类,在多层继承关系中,isntanceof运算符同样适用。
 
//定义构造函数
function C(){}
function D(){}
 var o=new C();
o instanceof C   //true   
o instanceof D   //false 因为D.prototype不在o的原型链上
o instanceof Object   //true   因为Object.prototype.isPrototypeOf(o)  返回true
C.prototype instanceof Object   //true 同上
 
C.prototype={}
var o2=new C();
o2 instanceof C   //true
o instanceof C    //false    C。prototype指向了一个空对象,这个空对象不在o的原型链上。
D.prototype =new C();       //继承
var o3=new D();
o3 instanceof D   //true
o3 isntanceof C   //true
谈到instanceof 我们要多插入一个问题,就是function的arguments,我们大家也许认为arguments是一个Array,但如果用instanceof去测试回发现arguments不是一个Array对象,尽管看起来很像。
 
第三种:Object.prototype.toString
这是对象的一个原生扩展函数,用来精确区分数据类型
var type=Object.prototype.toString
console.log(type.call(''))    //object String
console.log(type.call([]))    //object Array
console.log(type.call({}))   //object Object
console.log(type.call(false))   //object Boolean
console.log(type.call(null))    //object Null
console.log(type.call(undefined))   //object Undefined
console.log(type.call(function(){}))   //object Function
 
 
 
 
 
 
 
 

从toString()方法到Object.prototype.toString.call()方法的更多相关文章

  1. 利用Object.prototype.toString方法,实现比typeof更准确的type校验

    Object.prototype.toString方法返回对象的类型字符串,因此可以用来判断一个值的类型. 调用方法: Object.prototype.toString.call(value) 不同 ...

  2. Object.prototype.toString.call() 、 instanceof 以及 Array.isArray()判断数组的方法的优缺点

    1. Object.prototype.toString.call() 每一个继承 Object 的对象都有 toString 方法,如果 toString 方法没有重写的话,会返回 [Object ...

  3. 前端面试题1:Object.prototype.toString.call() 、instanceof 以及 Array.isArray()三种方法判别数组的优劣和区别

    1. Object.prototype.toString.call() 每一个继承 Object 的对象都有 toString 方法,如果 toString 方法没有重写的话,会返回 [Object ...

  4. instanceof, typeof, & Object.prototype.toString

    /** * * @authors Your Name (you@example.org) * @date 2016-11-18 09:31:23 * @version $Id$ */instanceo ...

  5. 类型判断----小白讲解typeof,instanceof,Object.prototype.toString.call()

    1.typeof只能判断基本类型数据, 例子: typeof 1 // "number" typeof '1' // "string" typeof true ...

  6. 关于toString()和valueOf()以及Object.prototype.toString.call()的结合理解

    一.先说说String(): String()是全局函数,把对象的值转换为字符串. 语法:String(obj); 任何值(对象)都有String()方法,执行过程是这样的:首先,如果该对象上有toS ...

  7. typeof 、Object.prototype.toString和 instanceof

    数据类型 js 基本类型包括:Undefined  symbol null string boolean number js 引用类型包括:object array Date RegExp typeo ...

  8. Object.prototype.toString.call(obj).slice(8,-1)

    1.Object.prototype.toString() 该方法返回描述某个对象数据类型的字符串,如自定义的对象没有被覆盖,则会返回“[object type]”,其中,type则是实际的对象类型. ...

  9. Object.prototype.toString.call()进行类型判断

    为什么类型判断用到Object.prototype.toString.call()进行类型判断,而不用typeof()呢? 然后翻了一下资料: Typeof 在使用 ]));/));));//[obj ...

随机推荐

  1. 【BZOJ4254】Aerial Tramway 树形DP

    [BZOJ4254]Aerial Tramway 题意:给你一座山上n点的坐标,让你在山里建m条缆车,要求缆车两端的高度必须相等,且中间经过的点的高度都小于缆车的高度.并且不能存在一个点位于至少k条缆 ...

  2. Mybatis 3.1中 Mapper XML 文件 的学习详解(转载)

    MyBatis 真正的力量是在映射语句中.这里是奇迹发生的地方.对于所有的力量,SQL 映射的 XML 文件是相当的简单.当然如果你将它们和对等功能的 JDBC 代码来比较,你会发现映射文件节省了大约 ...

  3. 简单的纯css重置input单选多选按钮的样式--利用伪类

    由于input单选多选的原生样式通常都不符合需求,所以在实现功能时通常都需要美化按钮 html <input type="radio" /> <input typ ...

  4. angular中的子路由用法

    Angular ui-route的用法 引入angular和使用angular子路由时需要的依赖模块angular-ui-route.js.并且在html中将路由要插入的位置写上.而在js部分中和an ...

  5. 2017 Multi-University Training Contest - Team 1—HDU6040

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6040 题意:不知道北航的同学为何解释题意之前都要想一段故事,导致刚开始题意不是很懂,题意就是给你n,m ...

  6. jquery.dragsort.js 实现拖拽过程遇到的问题

    .在IE下第一次拖动的时候,被拖动的li元素会不显示,查了很多资料发现是因为在IE中定位出了问题,li标签还在,只是位置计算出错.解决的办法是在li的css样式中position设置为relative ...

  7. 草莓糖CMT依旧强势,数字货币量化分析[2018-05-29]

    [分析时间]2018-05-29 17:45 [报告内容]1 BTC中期     MA 空头排列中长     MA 空头排列长期     MA 空头排列 2 LTC中期     MA 空头排列中长   ...

  8. Python3: Command not found(Mac OS)

    1. 第一步:查看以下路径是否安装有 Python 3.x # 打开以下目录, 版本号有可能不同 cd /usr/local/Cellar/python/3.5.2_3/bin # 查看当前目录的内容 ...

  9. 在django中实现支付宝支付(支付宝接口调用)

    支付宝支付 正式环境:用营业执照,申请商户号,appid 测试环境:沙箱环境:https://openhome.alipay.com/platform/appDaily.htm?tab=info 支付 ...

  10. C#版-Redis缓存服务器在Windows下的使用

    Redis缓存服务器是一款key/value数据库,读110000次/s,写81000次/s,因为是内存操作所以速度飞快,常见用法是存用户token.短信验证码等 官网显示Redis本身并没有Wind ...