Java 使用新操作符创建了多少个对象?

Java 使用新操作符创建了多少个对象?,java,Java,可能重复: 如果我写 String s= new String("how many object b created by this method "); 与这样做相比,将创建多少参考对象和对象: Sting s1="Is this method is good as compare to upper"; 使用String s1=“some String”不会创建新的字符串对象。已经存在每个字符串文本的现有字符串对象 具有相同值的字符串文字由单个字符串对象表示,因此如果使用String

可能重复:

如果我写

String s= new String("how many object b created by this method ");
与这样做相比,将创建多少参考对象和对象:

Sting s1="Is this method is good as compare to upper"; 
使用
String s1=“some String”
不会创建新的字符串对象。已经存在每个字符串文本的现有字符串对象

具有相同值的字符串文字由单个字符串对象表示,因此如果使用
String s1=“some String”;String s2=“一些字符串”两个
s1
s2
都引用相同的
“某些字符串”
对象


newstring(“…”)
创建一个新的String对象,该对象使用与String对象相同的数据作为传递给构造函数的值“…”。

使用
String s=newstring(“此方法创建了多少个对象b”)创建String类的新对象,并将字符串“此方法创建了多少对象b”传递给其构造函数

String s1=“此方法是否与上一种方法相比更好”“s1”是字符串文字。关于字符串文字:

每次你的代码 创建一个字符串文本,即JVM 首先检查字符串文本池。 如果字符串已存在于 池,对池的引用 实例返回。如果字符串 池中不存在新字符串 对象实例化,然后放置在 游泳池。Java可以做到这一点 优化,因为字符串是 不可变,可以在没有 对数据损坏的恐惧

上述概念与:;所有文字字符串和字符串值常量表达式都在Java中。因此,基本上,使用
strings1=“这个方法与上面的方法相比是否更好”“此方法与upper相比是好的”
不在池中时,code>才会创建新对象。

请考虑:

String s1 = new String("hi");
String s2 = new String("hi");
System.out.println(s1 == s2);
将打印
false

然而

String s1 = "hi";
String s2 = "h1";
System.out.println(s1 == s2);
将打印
true

将打印
false

这就是为什么在比较
String
s时应始终使用
String.equals,而不是
=

但不要相信我的话。。。查看Java语言规范的以下摘录:


有两种方法可以在Java中创建字符串对象:

  • 使用新操作符。比如说,

    String str=新字符串(“Hello”)

  • 使用字符串文字或常量表达式)。比如说,

    String str=“Hello”;(字符串文字)或
    字符串str=“Hel”+“lo”;(字符串常量表达式)

字符串文字池:

字符串分配,与所有对象一样 分配,在这两方面都很昂贵 还有记忆。JVM执行一些操作 实例化字符串时的技巧 文字,以提高性能和 减少内存开销。削减 创建的字符串对象数 在JVM中,String类保持 一串线。每次你的代码 创建一个字符串文本,即JVM 首先检查字符串文本池。 如果字符串已存在于 池,对池的引用 实例返回。如果字符串 池中不存在新字符串 对象实例化,然后放置在 游泳池


使用NEW关键字创建String对象始终会在堆中创建包含所需字符串的对象,并返回堆中已创建对象的引用


创建不带NEW关键字的String对象(使用literal)首先检查String literal池中具有相同数据的现有字符串,如果找到,将返回String literal池中的相同引用,否则,将在String literal池中创建新字符串并返回其引用。

String s1=NEW String(“hello”),在JVM级别创建了多少个引用?我知道两个对象:一个是在类加载“hello”时,另一个是在实际执行命令时。1个引用是s1,我怀疑还有第二个引用s2,它是类加载时“hello”字符串的结果,传递给“new string()”构造函数。在java中,我们无法在函数或构造函数中传递对象本身,只能传递引用。另外,应该有第三个参考s3,它应该是新字符串(“hello”)的结果,然后被分配到s1?两个注释:我很好奇“false”案例#5是否在较新版本的java(新优化?)中发生了变化,但今天运行它是完全相同的,而且也是相同的。另外,为了帮助他人,我发现
other.other
令人困惑,直到我意识到小写的
other
是一个一级深的包名,而不是缺少的变量或字段。
String s1 = "hi";
String s2 = new String("hi");
System.out.println(s1 == s2);
Thus, the test program consisting of the compilation unit (§7.3):

    package testPackage;
    class Test {
            public static void main(String[] args) {
                    String hello = "Hello", lo = "lo";
                    System.out.print((hello == "Hello") + " ");
                    System.out.print((Other.hello == hello) + " ");
                    System.out.print((other.Other.hello == hello) + " ");
                    System.out.print((hello == ("Hel"+"lo")) + " ");
                    System.out.print((hello == ("Hel"+lo)) + " ");
                    System.out.println(hello == ("Hel"+lo).intern());
            }
    }
    class Other { static String hello = "Hello"; }

and the compilation unit:

    package other;
    public class Other { static String hello = "Hello"; }

produces the output:

    true true true true false true

This example illustrates six points:

    Literal strings within the same class (§8) in the same package (§7) represent references to the same String object (§4.3.1).
    Literal strings within different classes in the same package represent references to the same String object.
    Literal strings within different classes in different packages likewise represent references to the same String object.
    Strings computed by constant expressions (§15.28) are computed at compile time and then treated as if they were literals.
    Strings computed by concatenation at run time are newly created and therefore distinct. 

The result of explicitly interning a computed string is the same string as any pre-existing literal string with the same contents.