为了能更好的操作基本类型值,JavaScript提供了3个特殊的引用类型:Boolean,Number和String。这些引用类型和传统对象相似,有自己的属性和方法,但也具备各自的特殊行为。
一 基本包装类型简介
我们知道,基本类型的值是没有属性和方法的,不能被改变的。但是上面3个特殊的引用类型赋予了可以操作基本类型值的方法:
1 var str1 = "hello world"; 2 var str2 = str1.sunstring(5);
从上面代码我们知道,str1是一个基本类型的字符串,但我们却用它调用了一个方法,并把返回值赋值给了str2。照理说基本类型值是没有方法的,那么这个操作是怎么实现的呢?
实际上JavaScript在读取一个基本类型值时,后台会有如下操作:
1, 创建基本包装类型(这里是String类型)的一个实例。
2, 在该实例上调用相关方法。
3, 立即销毁该实例。
所以实际上str1在调用方法时可以理解为执行了如下过程:
1 var s1 = new String(str1); 2 var str2 = s1.substring(5); 3 s1 = null;
注意:以上操作都是后台完成,我们并不能察觉到它。
普通引用类型和基本包装类型的主要区别在于对象的生存周期,使用new 操作符创建的对象在程序执行流离开当前作用域之前一直都存在于内存中,而后台创建的基本包装类型的对象只存在于一行代码的执行瞬间,而后立即被销毁了。这意味着我们可以为基本类型的值添加属性和方法,但最终他们不会被保留。
1 var str = "hello"; 2 str.name = "someText"; 3 str.say = function(){ 4 //some code; 5 }; 6 console.log(str.name);//undefined 7 str.say();//TypeError: str.say is not a function
再看下面的代码:
1 var str = new String("hello"); 2 typeof str;//"object" 3 console.log(str);//{0:"h",1:"e",2:"l",3:"l",4:"o",length:5}
可以看到,尽管可以显式的创建基本包装类型对象,但它完全背离了我们使用字符串类型来存储文本信息的初衷,所以,如无特别必要,我们建议不要显式的创建和使用它。
二 Boolean类型
Boolean类型是布尔值对应的引用类型。要创建Boolean对象可以像下面这样:
1 var BooleanObj = new Boolean(false);
但是有一个问题,请看下面代码:
1 var booleanObj = new Boolean(false); 2 var result = booleanObj && true; 3 console.log(result);//true
虽然booleanObj的值是false,但它本身是一个对象,我们知道,在进行逻辑运算时会触发隐式类型转换,所有对象都被转换为true,所以最终result的值为true。但这并不是我们希望的结果,所以在工作中最好不要使用Boolean对象。
三 Number类型
Number类型是数字对应的引用类型。可以显式的创建数字对象,与Boolean类型一样,如果是用new创建数字值,使用typeof检测会返回“object”。
另外Number对象提供了两个实用的方法:
1, toFixed()
接受一个数字作为参数,表示需要保留几位小数,返回字符串类型的数字。
1 var num1 = 10.005; 2 console.log(num1.toFixed(2));//"10.01"
2, toExponential()
接受一个数字作为参数,表示需要保留的小数位数,返回以指数形式表示的数字,也是字符串类型。
1 var num = 10; 2 console.log(num.toExponential(1));//”1.0e+1”
四 String类型
String类型是字符串包装类型。也可以显式的使用new创建字符串对象,但不建议。
String类型的每一个实例都有一个length属性,表示该字符串包含多少个字符。
1 var str = new String(“hello”); 2 console.log(str.length);//5
String类型提供了下列常用方法:
1, charAt()和charCodeAt()—获取某位置上的单个字符
1 var str = "hello world"; 2 console.log(str.charAt(0));//"h",str的第一个字符 3 console.log(str.charAt(str.length - 1));//"d",str的最后一个字符 4 console.log(str.charCodeAt(0));//104,str第一个字符的编码 5 console.log(str.charCodeAt(str.length - 1));//100,str最后一个字符的编码
2, concat()—拼接字符串
1 var str1 = "hello"; 2 var str2 = "world"; 3 console.log(str1.concat(str2));//"helloworld" 4 console.log(str2.concat(str1));//"worldhello"
3, substr()、substring()和slice()—复制字符串中的一部分
1 var str = "hello world"; 2 console.log(str.substring(0,5));//"hello" 3 console.log(str.substring(0));//"hello world" 4 console.log(str.slice(6));//"world" 5 console.log(str.slice(4,7));//"o w" 6 console.log(str.substr(0,4));//"hello" 7 console.log(str.substr(0));//"hello world"
从上面的例子可以看出,substring()和slice()一样,可以接受两个参数,第一个参数是开始位置,第二个参数是结束位置,最终返回这两个参数区间内的字符串(不包含结束位置)。substr()和他们有一点不同,第二个参数是需要截取的字符串个数,而不是结束位置的下标。
如果不提供第二个参数,那么他们都默认复制至末尾。
4, indexOf()和lastIndexOf()—查找子串在字符串中第一次出现的位置
1 var str = "hello world"; 2 console.log(str.indexOf("l"));//2 3 console.log(str.lastIndexOf("l"));//9
indexOf()是从前往后查找,lastIndexOf则是从后往前查找。
5, toLowerCase()和toUpperCase()—大小写转换
1 var str = "hello WORLD"; 2 console.log(str.toLowerCase());//"hello world" 3 console.log(str.toUpperCase());//"HELLO WORLD"
6, replace()—替换部分字符
1 var str = "hello world,hello world,hello world"; 2 console.log(str.replace("world","bokeyuan"));//"hello bokeyuan,hello world,hello world" 3 console.log(str.replace(/world/g,"bokeyuan"));//"hello bokeyuan,hello bokeyuan,hello bokeyuan",这里是使用了正则表达式全局匹配
replace()接受两个参数:第一个参数可以是字符串或正则表达式,表示被查找的子串。第二个参数可以是字符串或函数(有返回值),表示替换文本。函数接受3个参数,第一个是需要被替换的字符串,第二个是在字符串中出现的位子,第三个是被查找的字符串本身(str)。
7, split()--分割字符串
1 var str = "hello world"; 2 console.log(str.split("l"));//["he", "", "o wor", "d"]
接受一个参数,把字符串中出现的该参数作为分界点,分割字符串,返回一个数组。
8,trim()--去除字符串首尾空白字符
1 var str = " hello "; 2 console.log(str.trim());//"hello"
9, fromCharCode() –-将字符编码转换成字符
1 var str = String.fromCharCode(65,66,67); 2 console.log(str);//"ABC"
fromCharCode()是String的一个静态方法,所以它的调用和其他方法有点不一样。它接受一个或多个数字,把他们当做字符编码,并转换成相应的字符。