2、String类
2.1 String定义
String:字符串,使用一对""引起来表示
-
String声明为final,不可被继承
-
String实现了Serializable接口:表示字符串是支持序列化的
实现了Comparable接口:表示String可以比较大小
-
String内部定义了final char[] value用于存储字符串数据
-
String代表不可变的字符序列。具有不可变的特性
- 体现:当对字符串重新赋值、对字符串进行连接操作、调用replace()方法修改指定字符(串)时,需要重写指定内存区域赋值,不能使用原有的value进行赋值
-
通过字面量方式(区别于new方式)给字符串赋值时,此时字符串值声明在字符串常量池中
-
字符串常量池中不会存储相同内容的字符串
String实例化方式
-
字面量定义
String s1 = "hello";
-
new + 构造器
String s2 = new ("hello");
面试题:String s = new String(“abc”);在内存中创建了几个对象?
两个:一个是堆空间中new的对象,另一个是堆空间new的String对象的底层char[]对应常量池中的对象数据"abc"
2.2 字符串拼接
-
常量与常量的拼接结果在常量池
String s1 = "ab"+"cd";
final类型的字符串也是常量,拼接结果也在常量池
-
只要拼接的字符串里有一个是变量,拼接结果就在堆中new String对象,对象底层的char[]再指向常量池中的字符串值,若调用intern()方法则会返回常量池中的字符串值
String s2 = "" + s1;
2.3 字符串常用方法
- int length():返回字符串长度,return value.length
- char charAt(int index):返回指定索引处的字符,return value[index]
- boolean isEmpty():判断字符串是否为空,return value.length==0
- String toLowerCase():使用默认语言环境,将String所有字符转换为小写
- String toUpperCase():使用默认语言环境,将String所有字符转换为大写
- String trim():返回字符串的副本,忽略前导空白和尾部空白
- boolean equals(Object obj):比较字符串的内容是否相同
- boolean equalsIgnoreCase(String tr):与equals方法类似,忽略大小写
- String concat(String str):将指定字符串连接到此字符串结尾,str1.concat(str2)等价于str1+= str2
- int compareTo(String str):比较两个字符串的大小,负数小于,0相等,正数大于str(因为实现了Comparable接口,所以实现了抽象方法compareTo())
- String substring(int beginIndex):返回一个新的字符串,它是此字符串索引从beginIndex开始的子串
- String substring(int beginIndex,int endIndex):返回一个新的字符串,它是此字符串索引从beginIndex开始,到endIndex(不包含)结束的子串
- boolean endsWith(String str):是否以子串str结尾
- boolean startsWith(String str):是否以子串str开头
- boolean startsWith(String str,int idx):从索引开始的子串是否以子串str开头
- boolean contains(CharSequence s):此字符串是否包含指定的char序列
- int indexOf(String str):返回子串str在此字符串中第一次出现的索引
- int indexOf(String str,int idx):返回子串str在此字符串从idx索引处开始往右第一次出现的索引
- int lastIndexOf(String str):返回子串str在此字符串中最右边出现处的索引
- int lastIndexOf(String str,int idx):返回子串str在此字符串从idx索引处开始往左第一次出现的索引
注:indexOf和lastIndexOf方法如果未找到,返回值都是-1
在寻找的子串只出现一次或不存在时下indexOf和lastIndexOf返回值相同
- String replace(char oldChar,char new Char):返回一个用newChar代替该字符串中所有oldChar后的新字符串
- String replace(CharSequence target,CharSequence replacement):使用指定的字面值替换序列替换此字符串所有匹配字面值目标序列的子字符串
- String replaceAll(String regex,String replacement):使用给定的replacement替换此字符串中所有匹配给定正则表达式的子字符串
- String replaceFirst(String regex,String replacement):使用给定的replacement替换此字符串第一个匹配给定正则表达式的子字符串
- boolean matches(String regex):判断此字符串是否匹配给定的正则表达式
- String[] split(String regex):根据给定正则表达式的匹配拆分此字符串为字符串数组
- String[] split(String regex,int limit):根据给定正则表达式的匹配拆分此字符串为字符串数组,最多不超过limit个,如果超过了剩下的全部都放到最后一个元素中
2.4 与其他类型转换
-
基本数据类型、包装类
String → Xxx:包装类的静态方法xxx.parseXxx(str)
Xxx→String:String类重载的方法String.valueOf(xxx)
-
char[ ]
String→char[ ]:调用String的toCharArray()方法
char[ ]→String:调用String构造器,new String(char[ ])
-
byte[ ]
编码:String→byte[ ]:调用String的getBytes()
String str1 = "abc123中国"; byte[] bytes = str1.getBytes(); byte[] bytes1 = str1.getBytes("gbk");
解码:byte[ ]→String:调用String的构造器
String str2 = new String(bytes); String str3 = new String(bytes1,"gbk");
注:解码时使用的字符集必须与编码时使用的字符集一致,否则会乱码
2.5 StringBuffer、StringBuilder
- String:不可变的字符序列
- StringBuffer:可变的字符序列;线程安全,效率低
- StringBuilder:可变的字符序列;JDK5.0新增,线程不安全,效率高
同:底层都是用char[ ]存储,StringBuffer与StringBuilder都继承了AbstractStringBuilder抽象类
源码分析
String不可变所以用构造器创建时value初始化为给定的长度
StringBuffer在初始化时,
- 若调用空参构造器,value初始化为new char[16]
- 若调用参数为String str的构造器,value初始化为new char[str.length() + 16 ]
- 若调用参数为int capacity的构造器,value初始化为new char[ capacity ]
扩容问题:如果底层数组放不下要添加的字符串了,则需要扩容
默认情况下,扩容为原来容量的2倍+2,同时将原有数组中的元素复制到新的数组中
指导意义:开发中建议使用new StringBuilder(int capacity)或new StringBuffer(int capacity),避免自动扩容多次浪费时间
常用方法
修改自身的方法
- 增:append(String str):字符串后拼接字符串str
- 删:delete(int start,int end):删除 [start,end)范围内的字符串
- 改:
- setCharAt(int index,char ch):将index位置处字符替换为ch
- replace(int start,int end,String str):将[start,end)范围内的字符串替换为字符串str
- 查:int indexOf(String str)、char charAt(int index)
- 插:insert(int offset,String str):在offset位置插入字符串str
- reverse():将当前字符串逆转
- String substring(int start,int end)、int length()
我的学习笔记有更多精彩内容哦
Java编程知识专栏