我要提问的问题如下:
下面这个类一共创建了几个对象,它们分别在什么的方?
public class Test {
    public static void main(String[] args) {
      String s1=new String("abc");
      String s2="abc";
      String s3=new String("abc");
      System.out.println(s1==s2);
      System.out.println(s1==s3);
    }
}

解决方案 »

  1.   

    应该是创建了2个object,第2个是一个primitive type, 不过其实你也可以当作一个object来看。起码我感觉是差不多
      

  2.   

    对于程序来讲可以视作3个object,String是object,int才是primitive type.
    变量名其实类似与c++里面的pointer,<think in java>中把这个叫做reference,你用==其实相当于比较pointer
      

  3.   

    我感觉是三个, java中的所有的类型都当做参数看的            
                 String   s1=new   String( "abc "); 
                String   s2= "abc "; 
     没有差别System.out.println(s1==s2); 
      要写s1.euqals("s2")吧
    s1==s2判断的好像是地址
      

  4.   

    答:
    1)三个引用。
    2)s1引用的String对象的空间在堆中。s2引用的String对象在常量区中。其实就是一个字符序列。s3引用的String对象的空间在堆中。
      

  5.   

    使用new运算符新建String类对象,第二中方式是使用字符串常量赋值
    给引用。两个创建String对象的语句都是返回一个String对象的引用,
    但是在jvm对两者的处理方式是不一样的。对于第一种,jvm马上在堆中,创建一个String对象,然后将该对象的引用返回给用户。对于第二种,jvm首先会在内部维护的字符串池(String pool)中通过String的equals方法查找是
                对象池中是否存放有该String对象,如果有,返回已有的String对象给用户,而不会在堆中
                重新创建一个新的String对象;否则,jvm会创建新的String对象,将其返回给用户,同是将
                该引用添加到字符串池中。
     使用new创建对象是,jvm是不会主动把该对象放到字符串池里面的,除非程序调用String的intern方法。
      

  6.   


                String   s1=new   String( "abc "); 2个 堆1,字符串常量池1
                String   s2= "abc ";               1个 池1  
                String   s3=new   String( "abc "); 2个 堆1,字符串常量池1
                System.out.println(s1==s2);        false  比较地址s1在堆s2在池
                System.out.println(s1==s3);        false  在堆中的2片不同地方
      

  7.   


    3个引用和2个对象,String s2 = "abc";是在常量池中创建的,如果之前没有的话。这个是在编译期间产生的,存在于.class文件中。使用new产生的对象"abc"在堆内存中,是运行时产生的,同时也会到常量池去检查一下有没有"abc"存在在该例中常量池中在编译期就有了"abc"了,所以总共就是两个对象。
      

  8.   

    三个,String对象new和不new是在不同的内存中赋值的。new表示在不同的空间。而非new则是在常量池中,比如String a="asdf"; 表示常量池永远只有"asdf"这个值。
      

  9.   

    如果 StringPool 中的也算,是 3 个,否则 2 个。上面的解释很详细。
      

  10.   

    不错.
    脱离该例子.字符常量也是一个对象.所幸的是JAVA处理String常量的方式与其他语言的处理普通字符串的方式相同.
      

  11.   

    系统对所有的字符串常量和常值的String表达式都会自动地进行字符串扣留。 
    只有包含变量的String表达式需要显示的调用intern()进行扣留。什么是字符串扣留,每本java基础书上都有讲到吧?
      

  12.   

    public   class   Test   { 
            public   static   void   main(String[]   args)   { 
                String   s1=new   String( "abc ");//此处"abc"和 new   String( "abc ")生成2个对象
                String   s2= "abc "; //此处因为扣留机制,没有生成对象(*)
                String   s3=new   String( "abc ");//new   String( "abc ")生成一个对象
                System.out.println(s1==s2); 
                System.out.println(s1==s3); 
            } 
    }一共三个,所以你会打印出2个false;
    应该说在String   s2= "abc "; 这里,实现扣留机制应该先生成一个对象,然后又扣留将其销毁掉。
    可以这么说,是生成了4个对象,但销毁了1个。
    其实稍微想想,虚拟机应该不会这么烂(做生成再销毁的事情)。我比较支持3个的说法。
      

  13.   


    问一下,如何去常量池中检查?是用equals()方法么?
    如果是的话,用equals()方法应该是这样用吧:
    XXX.equals("abc"); --其中的XXX是什么?
      

  14.   

    一些教科书上,从java开始入手的时候就让人误解了些东西
    没有严格把引用和对象区分开来看,把引用和对象混为一谈,
    导致很多人不能正确理解引用和对象。。
      

  15.   

    应该时三个对象  new的值都要放在栈里面,每次new的话都要再开辟一个空间,但是要现在内存中查找时不时有这个值,如果有直接添加引用。
      

  16.   

    (下面来源于  【经典推荐】每个初学者都应该搞懂的问题  ) 这个S 貌似不是对象 是一个引用!!呵呵
    问题一:我声明了什么! String s = "Hello world!"; 许多人都做过这样的事情,但是,我们到底声明了什么?回答通常是:一个String,内容是“Hello world!”。这样模糊的回答通常是概念不清的根源。如果要准确的回答,一半的人大概会回答错误。 
    这个语句声明的是一个指向对象的引用,名为“s”,可以指向类型为String的任何对象,目前指向"Hello world!"这个String类型的对象。这就是真正发生的事情。我们并没有声明一个String对象,我们只是声明了一个只能指向String对象的引用变量。所以,如果在刚才那句语句后面,如果再运行一句: String string = s; 我们是声明了另外一个只能指向String对象的引用,名为string,并没有第二个对象产生,string还是指向原来那个对象,也就是,和s指向同一个对象。