常用API(String,ArrayList)
String
String类概述
-
String类定义的变量可以用于存储字符串,同时String类提供了很多操作字符串的功能,我们可以直接使用
-
java.lang.String 类代表字符串,String类定义的变量可以用于指向字符串对象,然后操作该字符串
-
特点:
String其实常被称为不可变字符串类型,它的对象在创建后不能被更改
以“”方式给出的字符串对象,在字符串常量池中存储,而字符串常量池存放于堆内存中
String name = "生产力"; name += “决定”; name += “生产关系”; System.out.println(name); // 生产力决定生产关系
这里看似“name”的值发生了更改,实际上并没有发生变化
image.png
“生产力决定”和“生产力决定生产关系”是运算所得的新的对象,不会存放于字符串常量池当中,因此,常量池中的对象并未发生变化,所以String的对象在创建后不能被更改这句话在这里也是正确的,打印结果发生变化是因为指向了新的运算结果对象
-
String是不可变字符串的原因的总结:
- String变量每次的修改其实都是产生并指向了新的字符串对象
- 原来的字符串对象都是没有改变的,所以称不可变字符串
String类创建对象的两种方式
-
方式一:直接使用“”定义
String name = "Java开发";
-
方式二:通过String类的构造器创建对象
构造器 说明 public String() 创建一个空白字符串对象,不含有任何内容 public String(String original) 根据传入的字符串内容,来创建字符串对象 public String(char[] chs) 根据字符数组的内容,来创建字符串对象 public String(byte[] chs) 根据字节数组的内容,来创建字符串对象 例子:
package com.java.test; public class StringWays { public static void main(String[] args) { String s1 = "操作系统"; System.out.println(s1); String s2 = new String(); System.out.println(); String s3 = new String("数据结构"); System.out.println(s3); char[] chars = {'c', 'n', '中', '国'}; String s4 = new String(chars); System.out.println(s4); byte[] bytes = {97, 98, 99, 65, 67, 66}; String s5 = new String(bytes); System.out.println(s5); } } /* 操作系统 数据结构 cn中国 abcACB */
-
区别点(面试常考)
-
以“”方式给出的字符串对象,在字符串常量池中存储,而且相同内容只会在其中存储一份
只存储一份的原因是为了节省内存空间,即创建形同的字符串对象实际上只会有一个存在
-
通过构造器new对象,每new一次都会产生一个新对象,放在堆内存中
例子:
package com.java.test; public class StringDmo { public static void main(String[] args) { // 在字符串常量池创建了相同的字符串对象"abc",只会存在一个 // 因为只存在一个字符串对象,指向的地址也是相同的 String s1 = "abc"; String s2 = "abc"; System.out.println(s1 == s2); //因为首先在堆内存中创建了数组对象 //s3是根据数组对象产生的字符串对象("abc") //s4也是根据数组对象产生的 //因此即便二者的内容相同,但是在堆内存中都指向了不同的地址,最后结果只能为false char[] chars = {'a','b','c'}; String s3 = new String(chars); String s4 = new String(chars); System.out.println(s3 == s4); } }
-
-
字符串对象特点总结:
- 不可变
- 双引号创建的字符串对象,如果相同则在字符串常量池只能存在一个
- new构造器创建的字符串对象,在堆内存中分开存储
String类常见面试题
-
String s2 = new String("abc"); String s1 = "abc"; sout(s1 == s2)
-
一共有几个对象
第一条语句创建了2个对象,一个“abc”位于常量池,另一个new出的“abc”位于堆内存
第二条创建了0个对象,第一行代码已经有“”产生的“abc”位于常量池中,这里的“”创建也会放入常量池,相同仅存留一个
-
运行结果
false,s1的地址是指向常量池的“abc”,s2的地址是指向堆内存中的“abc”
-
-
String s1 = "abc"; String s2 = "ab"; String s3 = s2 + "c"; sout(s1 == s3);
-
运行结果
false,s1的地址指向常量池的“abc”,s3的地址指向运算产生并存放在堆内存中的“abc”
-
-
String s1 = "abc"; String s2 = "a" + "b" + "c"; sout(s1 == s2);
-
运算结果
true,Java存在编译优化机制,程序在编译时"a" + "b" + "c"转换成“abc”
-
String类常用API—字符串内容比较
-
==:比较地址
用户输入的值(对象)在堆内存,和常量池的对象地址不同,使用==判断字面是相等会失败。
==不适合字符串内容比较,仅适用于基本数据类型的比较
-
equals():比较内容
方法名 说明 public boolean equals(Object anObject) 将此字符串与指定对象进行比较,只关心字符串内容是否一致 public boolean equalsIgnoreCase(String anotherString) 将此字符串与指定对象进行比较,忽略大小写比较字符串,只关心字符串内容是否一致 例如:adminName.equals(name); verificationCode.equalsIgnoreCase(code);
忽略大小写的字符串比较适用于比较验证码的业务逻辑
String常用API—遍历,替换,截取,分割操作
方法名 | 说明 |
---|---|
public int length() | 返回此字符串的长度 |
public char charAt(int index) | 获取指定索引位置处的字符 |
public char[] toCharArray(); | 将当前字符串转换成字符数组返回 |
public String substring(int beginIndex, int endIndex) | 根据开始&结束索引进行截取,得到新的字符串,不包括结束索引 |
public String substring(int begInIndex) | 从传入的索引处截取,截取到末尾,得到新的字符串 |
public String replace(CharSquence target, CharSquence replacement) | 使用新值,将字符串中的旧值替换,得到新的字符串 |
public String[] split(String regex) | 根据传入的规则切割字符串,得到字符串数组返回 |
public boolean contains(CharSquence s) | 判断是否包含指定字段 |
public boolean startsWith(String prefix) | 判断字符串是否指定字段开始 |
package com.java.test;
public class StringAPI {
public static void main(String[] args) {
// 1.public int length() 返回此字符串的长度
String name = "金银天然不是货币,但货币天然是金银";
System.out.println(name.length());
// 2.public char charAt(int index) 获取指定索引位置处的字符,注意索引遵循数组索引的原则即从0开始
System.out.println(name.charAt(8));
// 遍历字符串中的每个字符
for (int i = 0; i < name.length(); i++) {
System.out.print(name.charAt(i));
}
System.out.println();
// 3.public char[] toCharArray(); 将当前字符串转换成字符数组返回
char[] chars = name.toCharArray();
for (int i = 0; i < chars.length; i++) {
System.out.print(chars[i]);
}
System.out.println();
// 4.public String substring(int beginIndex, int endIndex)
// 根据开始&结束索引进行截取,得到新的字符串,不包括结束索引
String name2 = "Java是世界上最棒的编程语言";
System.out.println(name2.substring(0, 4));
// 5.public String substring(int begInIndex)
// 从传入的索引处截取,截取到末尾,得到新的字符串
System.out.println(name2.substring(4));
// 6.public String replace(CharSquence target, CharSquence replacement)
// 使用新值,将字符串中的旧值替换,得到新的字符串(记住加上双引号)
System.out.println(name2.replace("Java", "JavaScript"));
// 7.public String[] split(String regex) 根据传入的规则切割字符串,得到字符串数组返回
String name3 = "王宝强,贾乃亮,陈羽凡,谢霆锋";
String[] name4 = name3.split(",");
for (int i = 0; i < name4.length; i++) {
System.out.println(name4[i]);
}
// 8.public boolean contains(CharSquence s) 判断是否包含指定字段
System.out.println(name2.contains("JavaScript"));
// false,没有收到前面替换的影响是因为replace会生成新的字符串而不是改动原字符串
// 9.public boolean startsWith(String prefix) 判断字符串是否指定字段开始
System.out.println(name2.startsWith("Java"));
}
}
String类综合案例
-
String类开发验证码功能
需求:随机产生一个5位验证码,每位可能是数字,大写字母,小写字母
package com.java.test; import java.util.Random; public class VerificationNew { public static void main(String[] args) { // 1.定义可能出现的字符信息 String datas = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ01234567890"; // 2.循环5次,每次生成一个随机的索引,提取对应的字符连接起来即可 Random r = new Random(); String code = ""; for (int i = 0; i < 5; i++) { //随机一个索引 int index = r.nextInt(datas.length()); char c = datas.charAt(index); code += c; } System.out.println(code); } }
-
模拟用户登录功能
需求:模拟用户登录功能,最多只给三次机会
package com.java.test; import java.util.Scanner; public class StringLogin { public static void main(String[] args) { // 1. 定义正确的账号密码 String loginName = "admin"; String loginPassword = "Misaki1216"; // 2. 定义循环,循环3次,让用户登录 Scanner sc = new Scanner(System.in); for (int i = 1; i <= 3; i++) { System.out.println("请输入登录名:"); String name = sc.next(); System.out.println("请输入登录密码:"); String password = sc.next(); // 3. 判断登录是否成功 if (name.equals(loginName)) { if (password.equals(loginPassword)) { System.out.println("登录成功!"); break; } else { System.out.println("密码错误!"); System.out.println("您还剩余" + (3 - i) + "次登陆机会"); } } else { System.out.println("账号错误!"); System.out.println("您还剩余" + (3 - i) + "次登陆机会"); } } } }
-
手机号码屏蔽
需求:以字符串的形式从键盘接入一个手机号,将中间四位号码屏蔽,效果例如:155****8362
package com.java.test; import java.util.Scanner; public class PhoneNumber { public static void main(String[] args) { // 1. 键盘录入手机号码 Scanner sc = new Scanner(System.in); System.out.println("请您输入手机号码:"); String tel = sc.next(); // 2. 截取号码的前三位和后四位 String before = tel.substring(0, 3); String after = tel.substring(7); String s = before + "****" + after; System.out.println(s); } }
网友评论