string 是由final 修饰,所以不可以被继承
其中内部属性有
1.由final修饰的char类型的value数组,数组本身也是不可变的又被fina修饰,其内存地址不能变 所以导致字符串的值就不可变了,但是它的内存地址是可以变的(所有不被final修饰的对象都 可以变)
2.一个int类型的数hash,默认值是0 由于作为hash缓存用的,当调用过hashcode方法后其值会改变,当再次调用hashcode时会判断是否为0不是直接返回hash 缓存
3.由final修饰的和序列化有关的一个long类型的序列化id
和一个数组
5. 构造方法和一些操作字符串的方法
构造方法:
每次调用构造函数时会将传入的参数对应的char数组的内存地址赋值给新的字符串对象的char数组已达到对char数组的复用进而提高效率和资源的分配
例如:String a=new String("t");
String b="t";
对于a来说会 创建俩个字符串对象一个保存到堆中,一个保存到字符串常量池中
而a的引用的是堆中的那一个
过程大概:首先"t" ,会创建一个char数组 用于保存t 后调用toString() 方法变成字符串保存在字符串常量池中 而后利用这个字符串通过构造方法进行创建堆当中的那个字符串对象
所以两个字符串对象的值是一样的但是内存地址是不一样的,还有就是这两个字符串对象的char数组是一样的都指向同一个内存地址 这就是我前面所说的 达到char数组的复用而提高效率和资源的分配
对于 常见 的字符串相加的问题
例如:String a="t";
String b="d";
String c=a+b;
String d="t"+"d";
sout(c==d)
为false 是因为d这样的相加其实在编译期已经计算出最终的结果了所以相当于
String d="td"; 其在字符串常量池中
而c这样的相加其实是 先创建了一个StringBuffer 对象然后再用append()方法将b对象拼接后调用toString()方法转化为字符串 其在堆中
所以两个的内存地址是不一样的
补充:1.jdk7.0后字符串常量池在堆中
2.String类中hashcode的实现