字符串对象在任何一门编程语言中都是至关重要的,因为程序从输入端接收到的必然是字符,数字严格意义上也是字符,其原理大家都明白的,因为键盘上的每一个字符都有其对应的ACII码。
编程语言除了拥有共有的特性外,如判断,循环等这些基本的语法点外,必然有其独特的一面。字符串的某些处理便是最好的证明。
一,字符串常量与字符串池
先看代码片段一:
- char[] name = {'I','v','a','n','T','i','a','n'};
- String name1 = new String(name); //实例化一个字符串对象
- String name2 = new String(name); //实例化一个字符串对象
- System.out.println(name1 == name2);
- //输出结果
- false
在看代码片段二:
- String name3 = "IvanTian"; //字符串变量
- String name4 = "IvanTian";//与name1的值严格相同
- System.out.println(name3 == name4 );
- //输出结果
- true
不错,以上两个代码片段中,name1,name2指向的是对一个对象参考;name3,name4也是如此,但是为何片段的结果是false呢?在前面的博文中曾提到,比较对象实质内容是否相同,要用equals()函数而非操作符“==”,但是片段二为何是true呢?
这就是Java字符串的一个特性,字符串池,如图一所示:
图一
用“”写下的字符串成为字符串常量(String literal),既然是常量,写死了值且为乐节省内存考虑,自然就不用为常量分别建立String实例了。所以name3和name4指向的是内容相同(序列,大小写严格相同)的字符串,无论在程序代码中出现几次,JVM都只会建立一个String实例,并把它放在字符串池(String Pool)中。
综上分析,以下代码片段的结果就不言而喻了吧,自己分析结果吧!
- String name1 = new String("IvanTian");
- String name2 = new String("IvanTian");
- String name3 = "IvanTian";
- String name4 = "IvanTian";
- System.out.println(name3 == name4 );
- System.out.println(name1 == name2);
- System.out.println(name1 == name3);
若是操作符“==”全部换成equals()函数呢?结果又如何呢?
二,不可变动字符串
字符串的连接,我们很容易想到的是“+”来操作,很不错,至少熟练掌握了操作符的应用。事实上,在字符串中使用“+”不是明智之举。看下面的代码.
- String name = "Java";
- String name1 = name +"world";
- System.out.println(name1);
- //输出结果
- JavaWorld
将此段代码反编译,会出现如下结果:
- String s1 = "Java";
- String s = (new StringBuilder())builder.append(s).append("World").toString();
- System.out.builder(s);
反编译的结果表明:在使用“+”连接字符串的时候,会变成建立一个StringBuilder对象,使用其append()方法进行“+”左右的字符串附加,然后转换成toString()返回。
在看一个例子,输出“1+2+3+....+50”
- StringBuilder builder= new StringBuilder();
- for (int i = 1; i < 50; i++) {
- builder.append(i).append("+");
- }
- System.out.println(builder.append(50).toString());
- }
- //输出结果是:
- 1+2+3+4+5+6+7+8+9+10+11+12+13+14+15+16+17+18+19+20+21+22+23+24+25+26+27+28+29+30+31+32+33+34+35+36+37+38+39+40+41+42+43+44+45+46+47+48+49+50
整个程序只产生一个builder对象,且每次append()调用以后,都会返回到该对象,且最后toString()后输出,有且仅有一次输出.
字符串的重要性,你懂的,其他的相关函数,例如,charAt(),toUpperCase(),toLowerCase(),toCharArray()乃至一个重要的 datatype.parseDatatype(String s)等等常用函数,具体可以参考JDK7的API文档了。