【问题标题】:How do object references work in wrapper classes objects and custom objects?对象引用如何在包装类对象和自定义对象中工作?
【发布时间】:2021-10-31 07:13:08
【问题描述】:

考虑下面的代码:

class Student{
    int id;
    String name;
}

public class Main
{
    public static void main(String[] args) {
        
        Student s1 = new Student();
        s1.id = 10;
        s1.name = "student 1";
        
        Student s2 = new Student();
        s2.id = 20;
        s2.name = "student 2";
        
        Student s3 = s1;
        s3.name = "student 3";
        
        System.out.println(s1.id +" "+s1.name);
        System.out.println(s3.id +" "+s3.name);
    }
}

对于上面的代码,输出是:

10 student 3
10 student 3

但是当我使用整数对象、字符串对象或其他一些包装类对象时,输出是不同的。考虑下面的代码:

public class Main
{
    public static void main(String[] args) {
        
        Integer a = 10;
        Integer b = 20;
        Integer c = a;
        
        c = 30;
        
        System.out.println(a);
        System.out.println(c);
    }
}


上述代码的输出是:

10
30

在我的自定义对象中,如果我更改一个对象的值,那么两个对象的值都会更改,但为什么在 Integer 和 String 等对象中却不是这样。

我的困惑是引用如何在 Integer、String、Double 等类中工作。

【问题讨论】:

    标签: java object oop


    【解决方案1】:

    s1 指的是内存的一部分,我们称那部分为 A。将 s1 分配给 s3 后,s3 也将引用 A;这意味着 s1 和 s3 都有指向同一个内存块的指针。更改 s1 或 s3 实际上是更改该内存块中的数据;并且会影响两者。

    【讨论】:

      【解决方案2】:

      包装类是不可变的。这意味着如果我们想改变包装类的值,我们别无选择,只能为引用包装类的变量分配一个新值。因此,在提供的代码中,我们创建了三个可访问的Integer 实例(通过autoboxing):

      Integer a = 10; // 1st instance of Integer created
      Integer b = 20; // 2nd instance of Integer created
      Integer c = a;  // still 2 instances, c references the same Integer as a
          
      c = 30; // 3rd instance of Integer created
          
      System.out.println(a);
      System.out.println(c);
      

      我们可以通过稍微扩展代码使其可见:

      Integer a = 10; // 1st instance of Integer created
      Integer b = 20; // 2nd instance of Integer created
      Integer c = a;  // still 2 instances, c references the same Integer as a
      System.out.println(a == c); // will print "true", a and c reference the same exact Integer
          
      c = 30; // 3rd instance of Integer created
          
      System.out.println(a);
      System.out.println(c);
      System.out.println(a == c); // will print "false", a and c reference different Integers
      

      Ideone demo

      我们可以看到包装类型的引用没有得到任何特殊处理。其行为(除了自动装箱功能)与 Java 中的任何外部引用类型相同。

      【讨论】:

        【解决方案3】:

        你在比较苹果和橘子。

        在代码sn -p A

            Integer a = 10;
            Integer b = 20;
            Integer c = a;
            
            c = 30;
        

        您并未修改ac 引用的对象,而是为c 分配了一个新引用。

        在代码sn -p B

            Student s1 = new Student();
            s1.id = 10;
            s1.name = "student 1";
            
            Student s2 = new Student();
            s2.id = 20;
            s2.name = "student 2";
            
            Student s3 = s1;
            s3.name = "student 3";
        

        您没有为s3 分配新的对象引用,您正在修改s1s3 引用的对象。

        代码 sn-p 与代码 sn-p A 相同

            Student s1 = new Student();
            s1.id = 10;
            s1.name = "student 1";
            
            Student s2 = new Student();
            s2.id = 20;
            s2.name = "student 2";
            
            Student s3 = s1;
        
            s3 = new Student();
            s3.name = "student 3";
        

        【讨论】:

          猜你喜欢
          • 2013-07-28
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2019-03-31
          • 2018-08-30
          相关资源
          最近更新 更多