首页 > 代码库 > JavaScript隐式类型转换

JavaScript隐式类型转换

        编程中少不了将某个数据类型转换成另一种数据类型。其中通过函数或者方法调用以及强制转换称为显示转换,相反的,在"不知情"的情况下"有意"的进行的转换,则称为隐士转换。

运算符中的隐士类型转换

        比较常见隐士类型转换,很多语言中都存在的。这里仅仅说说JavaScript中存在的。

        1、"+"运算符

function add(){
     var a ='2';
     var b =2;
     var c = a + b;
     console.info(c);         //输出22
     console.info(typeof c);  //输出string
} 
add();

       这里js(ECMASCRIPT)引擎将会把b编程字符串‘2‘再与a进行连接,最后变成了"22"。很多语言的"+"运算符都是这样处理的。这一过程是隐式进行的,js引擎帮助我们完成的。而且利用"+"这个特性,可以很方便的将Number类型转换为string类型。例如:

var number = 12;
var c = '' + number;
console.info(typeof number);   //number
console.info(typeof c);        //string

       2、"-"运算符

       “-”可以是一元运算符(取负),也可以是二元运算符(减法),"-"也会进行隐式类型转换,例如

var var1 = 234;
var var2 ="432";
var c = var1 - var2;
console.info(c);              //-198
console.info(typeof c);       //number

      可以看出的是"-"的特性与"+"正好相反,会把字符串b隐士的转换成数字再进行减法运算。利用这个特性,可以很方便的将string转换为number

var var3 = '12';
var var4 = var3 -'';
console.info(var4);             //12
console.info(typeof var4);   //number

      3、* and \运算符

       和"+"、“-”乘法和除法也会进行隐式类型的转换(转换为number再进行计算)。

var var1 = "1";
var var2 = "2";
var var3 = "20";
var var4 = var1 * var2;
console.info(var4);          //2
console.info(typeof var4)    //number
var var5 = var4/var3 ;
console.info(var5);          //0.1
console.info(typeof var5);   //number

       4、递增递减操作符(前置、后置)

       这类操作符适用于任何数据类型的值,针对不同类型的值,该操作符遵循以下的转换规则:

       1、如果是包含有效数字字符的字符串,先将其转换为数值(同Number()),再执行加减操作,字符串变为数值变量

       2、如果不包含有效数字字符串,将变量的值置为NaN,字符串变量变为数值变量。

       3、如果是布尔值false,转换为0进行运算。

       4、如果是布尔值true,转换为1进行运算。

       5、如果是浮点数值,直接进行加减1操作。

       6、如果是对象,先调用对象对的valueOf()方法,之后按照前5点进行转换,如果结果是NaN,调用toString()方法后应用前面规则进行判断。

       5、逻辑操作符(!、&&、||)

           逻辑非(!)操作符首先通过Boolean()函数将他的操作值转换为布尔值,然后求反。

           逻辑与(&&)

           1、如果第一个操作数经Boolean()转换后为true,则返回第二个操作值,否则返回第一个值(不是Boolean()转换后的值)

           2、如果有一个操作值为null.返回null

           3、如果有一个操作值为NaN,返回NaN

           4、如果有一个操作值为undefined,返回undefined

           逻辑或(||),如果一个操作值不是布尔值,遵循以下规则:

           1、如果第一个操作值经Boolean()转换后为false,则返回第二个操作值,否则返回第一个操作值(非Boolean()转换后的值)

           2、对于undefined、null和NaN处理规则与逻辑与相同

        6、关系操作符(<,>,<=,>=)

           和上述操作符一样,关系操作符的操作值也可以是任意类型的,所以使用非数值类型参与比较时也需要系统进行隐式类型转换;

           1、两个操作值都是数值,直接比较

           2、两个字符都是字符串,字符串编码进行比较

           3、一个数值,另一个转换为数值进行比较

           4、一个操作数是对象,调用valueOf()|toString(),之后按照1、2进行比较

           5、一个操作值是布尔值,则将其转换为数值,再进行比较。

       tips:NaN是非常特殊的值,不和任何类型的值相等,包括自己,同时它与任何类型的值比较大小时都返回false。

       7、相等操作符== and ===

         相等操作符也会对操作值进行隐式转换后进行比较

         1、布尔值、字符串和数值进行比较,转换为数值之后在进行比较

         2、null与undefined是相等的

         3、与NaN判等,返回false

         TIPS: == 和 === 区别

          1、对于Array,Object等高级类型,两者无区别:进行“地址”比较

          2、对于基础类型==判断值是否相等,===不仅判断值,而且判断类型是否相等。

          3、基础类型与高级类型有区别:==将高级类型转化为基础类型,进行“值”比较,===直接返回false

语句中的隐式转换

       在JavaScript语法中也存在者隐式类型转换,其中有if,while,for in,for in在定义对象字面量时发生从标识符到字符串的隐式转换

 

var ary = [1,3,5,7];
for(var a in ary){
    alert(a + ": " + typeof a);
}

    数组的索引其实也是字符串类型。

      alert时存在的隐式转换

String.prototype.fn = function(){return this};
var a = 'hello';
alert(typeof a.fn()); //-->object
alert(a.fn()); //-->hello

     string原型上添加了fn方法,该方法返回this也就是当前的实例对象,无可厚非的是typeof a.fn()是Object类型,可以alert(a.fn())却将object对象隐式的转为了字符串"hello"显示。

     同理,数值类型的也一样:

Number.prototype.fn = function(){return this};
var a = 10;
alert(typeof a.fn());//-->object
alert(a.fn()); //-->10

总结

       我相信js中的隐式类型转换的怪癖不止这么一点点,由于js是一种弱类型的语言,造成了coding时的灵活性,可以将不同类型进行比较等操作(js隐式转换),这可能让人感觉的诧异和不舒服。这种机制是否容易出错,其实不必过于担心,因为大部分的情况下,我们不需要转换,我们很少进行不同类型的比较(若有,不是更方便了嘛)。


JavaScript隐式类型转换