In my first article, I introduced the major types of JS and used typeof for output viewing. I also mentioned that each function has its own internal attribute [[class]. This class refers to the internal classification of js. This class roughly includes two types: data type and constructor.
Introduction to JavaScript Types
We talked about several major data types of JS, and also used typeof to look at several simple data type values. So today let's have a broader understanding of this aspect of knowledge. See the code below.
var num = 123; var str = 'aflypig'; var bool = true; var arr = [1, 2, 3, 4]; var obj = {name:'aflypig', age:21}; var func = function(){ console.log('this is function'); } var und = undefined; var nul = null; var date = new Date(); var reg = /^[a-zA-Z]{5,20}$/; var error= new Error();
Obviously, we only used typeof to look at several commonly used data types last time, but this time there are some built-in constructors, as well as the Array type. So, getting to the point, how can we get these values accurately (again, this is not a variable, JS measures the type of value, the variable is the container for storing the value) data type?
In fact, there are four methods, but there is only one way to identify them completely and accurately, which is also a common problem in the interview process.
I. typeof
typeof num //number typeif str //string typeof bool //boolean typeof arr //object typeof obj //object typeof func//function typeof und //undefined typeof nul //object typeof date //object tyepof reg //object tyoeof error //object
Parsing: Typeeof recognizes simple primitive type values (such as number,string,boolean), but for complex types (Object,Array,Function), it only recognizes Function.
Unfined and null are inherently bug s in JS, where typeof `undefined'identifies the correct type values, but null is classified into the `Object' family. For the date & reg & error types here, which are post-instance objects, typeof does not identify their `constructors'(which are not data types here). Obviously typeof can't handle this complex type.
Summary: Typeof can be seen as a defined type within JS that returns its corresponding string. It does not go deep into the value itself, does not type conversion, and only returns its corresponding type value for the current value. The same data type operates the same through the typeof operator. It has no principle. That's how JS is defined. We just remember it.
2. instanceof
Judging by the above typeof, we know that it does not satisfy some pseudotypes created by built-in constructors. So, let's use constructors to look at their constructors and identify their types.
num instanceof Number //false str instanceof String //false bool instanceof Boolean //false arr instanceof Array //true obj instaneof Object //true func instanceof Function //true und instanceof Object //false nul instanceof Object //false date instanceof Date //true reg instanceof RegExp //true error instanceof Error //true
Resolution: Here we use instanceof to compound the judgement of whether or not it is the corresponding type. First, let's look at the false item, num str bool, which does not wrap encapsulated objects when using instanceof, and instanceof is based on
Three constructor s
num.constructor .name //Numer str.constructor.name //String bool.constructor.name //Boolean arr.constructor.name //Array obj.constructor.name //Objeact func.constructor.name //Function und.constructor.name // TypeError nul.constructor.name //TypeError date.constructor.name //Date reg.constructor.name // RegExp error.constructor.name //Error
Except for undefined and null type errors (both have no attribute values), all of the above can get the data types we want. But is that really the case?
// 1⃣️ var Structure = function (){ } var ins = new Structure(); ins.constructor.name //Structure //2⃣️ var Person = function(){} var Student = function(){} Person.prototype = new Student(); var obj = new Person(); obj.constructor === Student
Resolution: In the first case, we can't get the exact type names for the instances generated by our constructors, which may have prevented us from using this method.
In the second case, because the constructor of the object is `variable', `inaccurate', we still can not get the exact type through the constructor.
Summary: Through the constructor, we can get str num bool which can not be obtained by instance, but another problem arises. The variability of the constructor, because of its uncertainty, we can not judge the correct data type in many cases, so the method of using the constructor is almost useless.
IV[[class]]
Resolution: This [[class]] refers to the classification attributes hidden within javascript, which are unreadable, non-enumerative, non-modifiable, and non-configurable. The attributes of underscore appearing on both sides belong to the attributes supported by some browsers. [[]] The two parenthesized attributes belong to JavaScript internal attributes. I remember in the previous chapter that everything in JavaScript is an object, and we can force it to be converted into a string to expose its internal [[class]] properties.
Understanding the above methods, we found that they can only complete part of the type verification, some cases are variable and inaccurate.
Object.prototype.toString.call(num); // "[object Number]" Object.prototype.toString.call(str); // "[object String]" Object.prototype.toString.call(bool); // "[object Boolean]" Object.prototype.toString.call(arr); // "[object Array]" Object.prototype.toString.call(func); // "[object Function]" Object.prototype.toString.call(und); // "[object Undefined]" Object.prototype.toString.call(nul); // "[object Null]" Object.prototype.toString.call(date); // "[object Date]" Object.prototype.toString.call(reg); // "[object RegExp]" Object.prototype.toString.call(error); // "[object Error]" arr instanceof Array //true obj instaneof Object //true func instanceof Function //true und instanceof Object //false nul instanceof Object //false date instanceof Date //true reg instanceof RegExp //true error instanceof Error //true
We use Object's toString method to view the current object's data type. We see that using this method we can see the corresponding data type perfectly, which is exactly what we want, and each object has its own [[class]. We can understand that it is an internal classification made by JavaScript according to the built-in constructor.
How can we get less jqquery when native js is often used and difficult to demand?
The following is the jQuery sample code related to the jQuery.type() function:
jQuery.type( undefined ); // "undefined" jQuery.type( null ); // "null" jQuery.type( true ); // "boolean" jQuery.type( new Boolean(true) ); // "boolean" jQuery.type( 3 ); // "number" jQuery.type( new Number(3) ); // "number" jQuery.type( "test" ); // "string" jQuery.type( new String("test") ); // "string" jQuery.type( function(){} ); // "function" jQuery.type( new Function() ); // "function" jQuery.type( [] ); // "array" jQuery.type( new Array() ); // "array" jQuery.type( new Date() ); // "date" jQuery.type( new Error() ); // New support for "error" // jQuery 1.9 jQuery.type( /test/ ); // "regexp" jQuery.type( new RegExp("\\d+") ); // "regexp"
jquery is also implemented internally in the way we just mentioned [[class]], which returns a string fixed to lowercase letters.
We can write a line of code to simply implement the type method in jquery
function type(o){ var s = Object.prototype.toString.call(o); return s.slice(s.indexOf(" ")+1,s.length-1).toLowerCase(); }
type(false) //boolean
type({}) //object
type([]) //array
type("") //string
type(/^/) //regexp
Hope that through this superficial explanation can bring you some harvest, when you know that there is a suitable way in the end, you should think more about using other means to achieve, because doing so can expand your knowledge. For example, if we list them back and forth, I don't think many people will think about the inadequacies of constructor s and instance s and their scope of application.