JavaScriptで型判定いろいろ
型の判定をするときに「typeof」とか「instanceof」とか「==」とかしょっちゅう忘れる。
あとDOM要素もwindowだったりHTMLElementParagraphElementとかいろいろあってややこしや。
この辺、jQueryのisArray()やisFunction()ではどうやってるんだろと見てみると、「Object.prototype.toString.call(v)」でやってた。
いろいろな型で試してみたところ、これで全部いけるじゃん!と分かったので、まとめたやつを作ってみた。
・type.js
/** * Decision type of variable. * @class Type * @static */ var Type = { isObject: function(v) { return (Object.prototype.toString.call(v) == "[object Object]"); }, isFunction: function(v) { return (Object.prototype.toString.call(v) == "[object Function]"); }, isArray: function(v) { return (Object.prototype.toString.call(v) == "[object Array]"); }, isBoolean: function(v) { return (Object.prototype.toString.call(v) === "[object Boolean]"); }, isString: function(v) { return (Object.prototype.toString.call(v) === "[object String]"); }, isNumber: function(v) { return (Object.prototype.toString.call(v) === "[object Number]"); }, isElement: function(v) { var check = false; switch(Object.prototype.toString.call(v)) { case "[object Object]": if (v.length) check = true; break; case "[object Window]": case "[object HTMLParagraphElement]": if (! Type.isUndefined(v) && ! Type.isNull(v)) check = true; break; default: break; } return check; }, isElementCollection: function(v) { return (Object.prototype.toString.call(v) === "[object HTMLCollection]"); }, isNull: function(v) { return (v === null); }, isUndefined: function(v) { return (v === 'undefined'); }, /** * @method getType * @param {Any} v The variable * @return {String} type of the variable */ getType: function(v) { if (Type.isNull(v)) { return "null"; } if (Type.isUndefined(v)) { return "undefined"; } if (Type.isElement(v)) { return "HTMLElement"; } return Object.prototype.toString.call(v).split(" ")[1].replace("]", ""); } };
・test.js
$(function() { var str = "abc"; console.log(Type.getType(str)); // String var num = 100; console.log(Type.getType(num)); // Number var arr = []; console.log(Type.getType(arr)); // Array var obj = {}; console.log(Type.getType(obj)); // Object var func = function() {}; console.log(Type.getType(func)); // Function var etc1 = {}; console.log(Type.getType(etc1.hoge)); // undefined var etc2 = null; console.log(Type.getType(etc2)); // null var el1 = document.getElementById("test1"); console.log(Type.getType(el1)); // HTMLElement var el2 = $("#test2"); console.log(Type.getType(el2)); // HTMLElement var el3 = document.getElementById("test3"); console.log(Type.getType(el3)); // null var els1 = document.getElementsByClassName("tests"); console.log(Type.getType(els1)); // HTMLCollection var els2 = document.getElementsByTagName("p"); console.log(Type.getType(els2)); // HTMLCollection var els3 = document.getElementsByClassName("testsss"); console.log(Type.getType(els3)); // HTMLCollection });
・test.html
<!doctype html> <html> <head> <meta charset="utf-8" /> <title>Type test</title> <script type="text/javascript" src="jquery-1.3.2.js"></script> <script type="text/javascript" src="type.js"></script> <script type="text/javascript" src="test.js"></script> </head> <body> <p id="test1" class="tests">Test用文字列</p> <p id="test2" class="tests">Test用文字列</p> </body> </html>
jQueryオブジェクトもHTML要素とみなしてます。オブジェクトとみなしてもいいのだけど、結局DOMとして扱うし。
nullとundefinedはtoString()で[object Window]が返ってくるので最初に判定する必要があります。
JavaScriptの型判定は割とバグの原因になりやすいので、前回書いたチーム開発の統一すべき項目に入れてもいいかも。