String字符串的存储原理
- 关于java 的jdk中内置的一个类:java.lang.String
- String表示字符串类型,属于引用数据类型,不属于基本数据类型
- 在java中随便使用双引号括起来的都是String对象
- java中规定,双引号括起来的字符串,是不可变的,也就是说“abc”自出生到最终死亡,不可变,不能变成“abcd",也不能变成”ab"
- 在JDK当中双引号括起来的字符串,例如:“abc","def"都是直接存储在方法区的字符常量池当中的
- 垃圾回收器是不会释放常量的
- 为什么sun公司把字符串存储在一个”字符串常量池“当中呢。因为字符串在实际开发中使用太频繁,为了执行效率,所以把字符串放到了方法区的字符串常量池当中。
- 关于String类中的构造方法
- 第一个:String s= new String("")
- 第二个:String s=""; 最常用
- 第三个:String s= new String(char 数组);
- 第四个:Sting s=new String(char数组,起始下标,长度):
- 第五个:String s= new String(byte 数组);
- 第六个:Sting s=new String(byte数组,起始下标,长度):
- 一些常用的方法:
- contains
- equals
- 比较两个字符串必须使用equals方法,不能使用“==”
- compareTo
- endsWith
- equalsIgnoreCase
- 判断两个字符串是否相等,并且同时忽略大小写
- indexOf
- 判断某个子字符串在当前字符串中第一次出现处的索引
- lastIndexOf
- 判断某个子字符串在当前字符串中最后一次出现处的索引
- isEmpty
- 判断某个字符串是否为空
- 面试题:判断数组长度和判断字符串长度不一样
- 判断数组长度是length属性,判断字符串长度是length()方法
- replace
- 使用指定的字面值替换序列 替换此字符串所有匹配字面值目标序列的子字符串
- lastIndexOf
- 判断某个子字符串在当前字符串中最后一次出现的索引(下标)
- startsWidth
- 判断某个字符串是否以某个子字符串开始、
- endsWith
- subString
- 截取字符串
- toLowerCase
- 转小写
- toUpperCase
- 转大写
- trim
- 去除字符串首尾的空白
- String中只有一个方法是静态的,不需要new对象,这个方法叫valueOf。作用是将非字符串转换成字符串
- 在实际开发中,如果需要进行字符串的频繁拼接,会有什么问题?
- 因为java中的字符串是不可变的,每一次拼接都会产生新字符串。这样会占用大量的方法区内存,造成内存空间的浪费。
String s=“abs”;
s+=“sdf”;
以上代码,导致在方法区字符串常量池当中创建了3个对象。“abs" , “sdf”,“abssdf”
如果以后需要进行大量字符串的拼接操作,建议使用JDK中自带的:
- java.lang.StringBuffer
- java.lang.StringBuilder
- 两者的区别
- StringBuffer中的方法都有:synchronized关键字修饰,表示StringBuffer在多线程环境下运行是安全的
- StringBuilder:无synchronized关键字修饰,非线程是安全的
- java中为8种基本数据类型又对应准备了8种包装类型。8种包装类型属于 引用数据类型,父类为object
- 为什么提供包装类?
- 因为8种基本数据类型不够用
- 这种包装类在实际开发中,我们不需要自己写。8种基本数据类型对应的8种包装类,sun公司已经写好了。直接用。
- 8种基本数据类型对应的包装类型名是什么?
基本数据类型 | 包装类型 |
byte | java.lang.Byte |
short | java.lang.Short |
int | java.lang.Integer |
long | java.lang.Long |
float | java.lang.Float |
double | java.lang.Double |
char | java.lang.Character |
boolean | java.lang.Boolean |
- 8种包装类中其中6个都是数字对应的包装类,他们的父类都是number,可以县研究一下number中公共的方法:
- number是抽象类,无法实例化对象
- 基本数据类型-- 转换为 — 引用数据类型 叫做 装箱
- 引用数据类型-- 转换为 — 基本数据类型 叫做 拆箱
- 在jdk1.5之后,支持自动拆箱和自动装箱了
- Integer的构造方法
- 构造方法有两个
- Integer(int)
- Integer(String)
- String为啥是不可变的:
- string类中有一个byte数组,并且这个byte数组是使用final修饰的。因为数组一旦创建,长度不可变,并且被final修饰的引用一旦指向某个对象之后,不可再指向其他对象,所以string是不可变的。
- stringBuilder or stringBuffer 为什么是可变的:
- 这两内部实际上是一个byte[]数组,这个byte[]数组没有被final修饰。stringBuilder or stringBuffer的初始化容量我记得是16.当存满之后回进行扩容,底层调用数组拷贝的方法 system.arraycopy()…是这样扩容的。所以。。。