JS-データタイプ-typeof/instance of/Object.prototype.toString
7092 ワード
参考記事:データの種類
typeof演算子 typeof演算子 instance of演算子 Object.prototype.toString方法 typeof値、文字列、ブール値はそれぞれ 関数は
実際のプログラミングでは、この特徴は判断文によく使われます.オブジェクトは nullはObjectに戻ります. 以下のコードにおいて、オブジェクト は、
短所:
さらに、は
Object.prototype.toStringオブジェクト、配列、関数を区別するためには、単に 私たちは、あるオブジェクト値がどの内蔵タイプに属するかを はどうして いくつかのプロトタイプチェーンの概念を簡単に説明します.
したがって、オブジェクトのタイプ
typeof演算子
JavaScript
には3つの方法があり、1つの値がどのタイプであるかを判定することができる.typeof
演算子は、値のデータタイプを返します.number
、string
、boolean
、function
を返します.typeof 123 // "number"
typeof '123' // "string"
typeof false // "boolean"
undefined
を返します.function f() {}
typeof f
// "function"
undefined
はtypeof
に戻る.typeof undefined
// "undefined"
この点を利用して、v
は、エラーを報告することなく、宣言されていない変数をチェックするために使用されてもよい.v
// ReferenceError: v is not defined
typeof v
// "undefined"
上記のコードの中で、変数var
はtypeof
コマンドで宣言していません.直接使用するとエラーが発生します.しかし、undefined
の後ろに置くと、エラーを報告せずにobject
に戻ります.実際のプログラミングでは、この特徴は判断文によく使われます.
//
if (v) {
// ...
}
// ReferenceError: v is not defined
//
if (typeof v === "undefined") {
// ...
}
typeof
に戻る.typeof window // "object"
typeof {} // "object"
typeof [] // "object"
object
の欠点:上のコードでは、空配列([])のタイプもJavaScript
であり、これはtypeof
内部であり、配列は本質的には特殊なオブジェクトであることを示している.instanceof
は、配列とオブジェクトを区別することができません.ちなみに、null
演算子は、行列とオブジェクトを区別することができます.var o = {};
var a = [];
o instanceof Array // false
a instanceof Array // true
instanceof
は空のオブジェクトの参照と見なされるからである.typeof null // "object"
instance ofv
演算子は、オブジェクトがあるコンストラクタの一例であるかどうかを示すブール値を返します.Vehicle
は構成関数true
の例であるので、instanceof
に戻る.var v = new Vehicle();
v instanceof Vehicle // true
instanceof
演算子の左側はインスタンスオブジェクトで、右側はコンストラクタです.prototype
の役割:右のコンストラクタのプロトタイプオブジェクト(Object.prototype.isPrototypeOf
)が、左のオブジェクトのプロトタイプチェーン上にあるかどうかを確認する.したがって、次の2つの書き方は等価です.v instanceof Vehicle
//
Vehicle.prototype.isPrototypeOf(v)
上記のコードにおいて、instanceof
の意味は以下の通りである.var p = {x:1};//
var o = Object.create(p);//
p.isPrototypeOf(o);//=>true:o p
Object.prototype.isPrototypeOf(p);//=> true p Object.prototype
true
によってプロトタイプチェーン全体を検査するので、同一のインスタンスオブジェクトは、複数のアーキテクチャ関数をd
に返すかもしれない.var d = new Date();
d instanceof Date // true
d instanceof Object // true
上記のコードでは、Date
は、Object
およびtrue
の例であり、したがって、これらの2つの構成関数はinstanceof
に戻る.prototype
の原理は、左のオブジェクトのプロトタイプチェーン上にあるかどうかを検査することである.左のオブジェクトのプロトタイプチェーンには、null
オブジェクトしかありません.このとき、instanceof
は歪みがあると判断する.var obj = Object.create(null);
typeof obj // "object"
Object.create(null) instanceof Object // false
上記のコードでは、Object.create(null)
は新しいオブジェクトobj
を返します.その原型はnull
です.右の構造関数Object
のprototype
属性は、左のプロトタイプチェーンにはないので、instanceof
はobj
がObject
の例ではないと考えられている.しかし、オブジェクトのプロトタイプがnull
でない限り、instanceof
演算子の判断は歪みません.instanceof
演算子の一用途は、判定値の種類である.var x = [1, 2, 3];
var y = {};
x instanceof Array // true
y instanceof Object // true
上記のコードにおいて、instanceof
演算子は、変数x
が配列であり、変数y
がオブジェクトであると判断した.短所:
instanceof
演算子は、元のタイプ(Unidefined、Null、Boolean、Number、String)の値を適用しないオブジェクト(純粋なオブジェクトと配列)にのみ使用できます.var s = 'hello';
s instanceof String // false
上記のコードでは、文字列はString
オブジェクトの例ではないので、false
を返します.さらに、
undefined
およびnull
については、instanceOf
演算子は常にfalse
に戻る.undefined instanceof Object // false
null instanceof Object // false
instanceof
演算子を利用して、構造関数を呼び出したときにnew
コマンドを追加することを忘れた問題も巧みに解決できます.function Fubar (foo, bar) {
if (this instanceof Fubar) {
this._foo = foo;
this._bar = bar;
} else {
return new Fubar(foo, bar);
}
}
上記のコードはinstanceof
の演算子を使用しており、関数内部でthis
のキーワードが構造関数Fubar
の例であるかどうかを判断している.もしそうでないなら、new
コマンドを追加するのを忘れたということです.Object.prototype.toString
typeof
を使用してはいけません.null
及びArray
の結果もobject
であり、時には必要なのは純粋なobject
オブジェクトである.Object.prototype.toString
法で正確に判断できます.Object.prototype.toString
方法を紹介する前に、toString()
方法とObject.prototype.toString.call()
方法を比較します.var arr=[1,2];
// toString()
arr.toString();// "1,2"
// call arr Object.prototype toString
Object.prototype.toString.call(arr); //"[object Array]"
継承配列arr
としてtoString
方法を書き換えたが、Object.prototype
におけるtoString
方法ではない.toString
と違って作用しますか?実は、この中はjs
プロトタイプとプロトタイプチェーンに関する知識があります.var arr=[1,2,3];
Object.prototype.toString.call(arr); //"[object Array]"
Array.prototype.toString.call(arr); // "1,2,3"
arr.toString(); // "1,2,3"
ここを見て分かるはずですが、複雑なデータタイプの判断にはObject.prototype
上のtoString
しか使えません.js
のオブジェクトは全部Object
から継承されていることを知っています.だから、あるオブジェクトに方法を呼び出すと、まずそのオブジェクトの上で調べます.もし見つからなかったら、対象の原型(つまり.prototype
)に入ります.見つけられなかったら、同じようなものも対象の原型に入ります.プロトタイプチェーンのトップObject.prototype
が見つかり、または入るまで停止します.したがって、
arr.toString()
を使用すると、Array.prototype.toString
を呼び出しているので、複雑なデータタイプの判断ができない.Array
もObject
から継承されているが、js
はArray.prototype
にtoString
に書き換えられ、Object.prototype.toString.call(arr)
を介して実際にはプロトタイプチェーンでObject.prototype.toString
を呼び出した.JavaScript
はすべて対象であり、例外ではない.すべての値タイプにObject.prototype.toString.call()
を適用する方法の結果は以下の通りである.console.log(Object.prototype.toString.call(123)) //[object Number]
console.log(Object.prototype.toString.call('123')) //[object String]
console.log(Object.prototype.toString.call(undefined)) //[object Undefined]
console.log(Object.prototype.toString.call(true)) //[object Boolean]
console.log(Object.prototype.toString.call({})) //[object Object]
console.log(Object.prototype.toString.call([])) //[object Array]
console.log(Object.prototype.toString.call(function(){})) //[object Function]