0151 /** 0152 * Initializes a newly created {@code String} object so that it represents 0153 * the same sequence of characters as the argument; in other words, the 0154 * newly created string is a copy of the argument string. Unless an 0155 * explicit copy of {@code original} is needed, use of this constructor is 0156 * unnecessary since Strings are immutable. 0157 * 0158 * @param original 0159 * A {@code String} 0160 */ 0161 public String(String original) { 0162 int size = original.count; 0163 char[] originalValue = original.value; 0164 char[] v; 0165 if (originalValue.length > size) { 0166 // The array representing the String is bigger than the new 0167 // String itself. Perhaps this constructor is being called 0168 // in order to trim the baggage, so make a copy of the array. 0169 int off = original.offset; 0170 v = Arrays.copyOfRange(originalValue, off, off + size); 0171 } else { 0172 // The array representing the String is the same 0173 // size as the String, so no point in making a copy. 0174 v = originalValue; 0175 } 0176 this .offset = 0; 0177 this .count = size; 0178 this .value = v; 0179 }注意看注释,除非要显式复制一个字符串,否则这个方法是没必要的
0152 * Initializes a newly created {@code String} object so that it represents
0153 * the same sequence of characters as the argument; in other words, the
0154 * newly created string is a copy of the argument string. Unless an
0155 * explicit copy of {@code original} is needed, use of this constructor is
0156 * unnecessary since Strings are immutable.
0157 *
0158 * @param original
0159 * A {@code String}
0160 */
0161 public String(String original) {
0162 int size = original.count;
0163 char[] originalValue = original.value;
0164 char[] v;
0165 if (originalValue.length > size) {
0166 // The array representing the String is bigger than the new
0167 // String itself. Perhaps this constructor is being called
0168 // in order to trim the baggage, so make a copy of the array.
0169 int off = original.offset;
0170 v = Arrays.copyOfRange(originalValue, off, off + size);
0171 } else {
0172 // The array representing the String is the same
0173 // size as the String, so no point in making a copy.
0174 v = originalValue;
0175 }
0176 this .offset = 0;
0177 this .count = size;
0178 this .value = v;
0179 }注意看注释,除非要显式复制一个字符串,否则这个方法是没必要的
怎么没在一块。
对于String s=new String("ddd");
(1)首先在堆中创建一个包含指定内容的字符串对象,并将字符串引用(s1)指向该对象;
(2)去字符串常量池查看,是否包含该内容的对象;
(3)若有,则在字符串常量池中内容相同的对象与new出来的字符串对象联系起来,若没有,则在字符串常量池再创建一个包含该内容的字符串对象,并将堆中的对象与字符串常量池中创建出来的对象联系起来。
楼主说的data区应该是常量池吧。
所以,最后应该是在堆和常量池都有了“ddd"这个字符串;
我们可以通过intern()方法来验证,因为此方法的作用是将字符串对象在字符串常量池中对应对象的引用返回,如果一开始没有关联,是无法返回字符串常量池中对应的引用的。
另外,常量池其实也是堆的一部分区域,不要以为是不同的区域。
(1)首先在堆中创建一个包含指定内容的字符串对象,并将字符串引用(s1)指向该对象;
(2)去字符串常量池查看,是否包含该内容的对象;
(3)若有,则在字符串常量池中内容相同的对象与new出来的字符串对象联系起来,若没有,则在字符串常量池再创建一个包含该内容的字符串对象,并将堆中的对象与字符串常量池中创建出来的对象联系起来。
楼主说的data区应该是常量池吧。
所以,最后应该是在堆和常量池都有了“ddd"这个字符串;
我们可以通过intern()方法来验证,因为此方法的作用是将字符串对象在字符串常量池中对应对象的引用返回,如果一开始没有关联,是无法返回字符串常量池中对应的引用的。
另外,常量池其实也是堆的一部分区域,不要以为是不同的区域。