本人初学java,以上为对学习过程中遇到的问题的个人理解,有误请指正,轻喷。
比较两个字符串是否为对称字符串(如abba)可以用到StringBuilder类的reverse()方法,判断反转后的字符串与原字符串的内容是否相等
如果相等,则为对称字符串,反之为不对称字符串,但比较字符串是否相等这里涉及到了是用==还是用string类的equals()方法,结论是用equals()方法
正确代码如下:
//代码如下
//创建键盘录入对象,并输入待比较字符串
Scanner sc = new Scanner(System.in);
System.out.println("请输入一个字符串;");
String s1 = sc.nextLine();
//用StringBuilder类的reverse()方法实现字符串的反转
//构造方法将String转换为StringBuilder
StringBuilder s = new StringBuilder(s1);
//调用成员方法反转
s.reverse();
//调用StringBuilder类的toString()方法将StringBuilder转换为String
String s2 = s.toString();
if(s1.equals(s2)){
System.out.println("该字符串为对称字符串");
}else{
System.out.println("该字符串不为对称字符串");
}
运行该代码,输入abba,显示为"该字符串为对称字符串"
但是,如果把上述代码的if语句中的条件改为s1 == s2,输入abba则会显示”该字符串不为对称字符串"
这是因为==号比较的是两个字符串的地址,而equals()比较的是字符串的内容是否相等
而s1和s2的内容相同但地址不同,以我的了解,s1是通过键盘录入的方式直接赋值的,因此它不经过堆而是直接在方法区的常量池里面开辟了一个空间存放该值,并将该地址给栈中的String类对象s1(假设地址为001);s2是来自于StringBuilder类转换过来的String类,由
StringBuilder s = new StringBuilder(s1)可知,该StringBuilder类在堆中开辟了一个空间,其转换为String类后存放的是s2在方法区的常量池里面的地址,而s1和s2的内容相同,因此在堆中存放的地址也是001,假设堆的地址为002,而String类s2栈中存放的就是堆的地址002,故s1和s2的地址不同,所以不能用"=="号而用equals()。
说白了,就是由于s2创建了StrinBuilder类,经过了堆这个中介到方法区的常量池,而s1直接到方法区的常量池,s2存放的是堆地址,而s1直接存放常量池地址。
什么是方法区的常量池?
方法区的常量池用来存放创建的String类对象的内容,相同的内容地址是相同的,优点是便于重复使用
例如:String s3 = "abba";
String s4 = "abba";
if(s3 == s4){
System.out.println("两者地址相同");
}
两个字符串的内容相同,因此地址相同。
String类对象中,如果只是判断内容是否相同就equals()方法,如果判断地址是否相同则用“==”号。