Frage

Please have a look at the code below:

class Parent{}

class Child : Parent
{
    public int field 
    {
        get; 
        set;
    }
}

class Program
{
    static void Main(string[] args)
    {
        Child child1 = new Child();
        Child child2 = child1;              //same memory address?

        child1.field = 12;
        child2.field = 14;

        Console.WriteLine(child1.field);    //14, as expected

        child1 = null;
        Console.WriteLine(child2.field);    //expected to crush: 'child1' is null so expected 'child2' to also be null

        Console.ReadLine();
    }
}

I expected this code to crash, but it does not not.

Why?

War es hilfreich?

Lösung

That's not how references work.

Child child1 = new Child();

creates a reference to a new Child object

Child child2 = child1;  

Creates another reference that points to the same object that child1 does

child1 = null;

Sets the child1 reference to null (it no longer points to anything). It does not change the object it pointed to and does not affect child2. child2 still points to the same object it did before.

Andere Tipps

First you create a child object and assign it to the variable child1

Child child1 = new Child();

So you can think of it looking like this, child1 points to an instance of a Child object

child1 ---->  { Child object }

Then you do this:

Child child2 = child1;

This copies the reference so now both variable points to the same object:

child1 ---->  { Child object }
child2 ------------^

Then you do this:

child1 = null;

This removes from the variable child1 the reference to the instance of the Child object. The important point here is that the Child object itself is unaffected by this:

child1        { Child object }
child2 ------------^

So since child2 had a copy of the reference, it is unaffected too and still points to the instance of Child you created at the start.

No, you are just setting the reference value contained in the child1 variable to the null value.
The second object instance still contains the original reference value and still works

In a very simplified way, when you write

Child child1 = new Child();

the child1 instance is created in memory and a reference to it is returned with a value that we could represent as the value 1000. This value (the reference) is assigned to the child1 variable

Child child2 = child1;              

You assign the same reference value 1000 to the second variable

child1 = null;

You set the variable child1 the value zero (or whatever the implementers of null decide null to be), but the chidl2 still contains the reference value 1000.

Still having a valid reference to the memory area where the original object has been created correctly blocks the Garbage Collector from removing the object from memory and you could still safely use the second variable

Yes when you assign a object to another object of the same class, the memory address or the reference is same.

But when you do child1=null;, the child2 still references the same object that it referenced during its initialization.

Unlike value-typed variables, reference variables are merely pointers towards an object instance. You can have multiple variables pointing to the same object; setting one of them to null doesn't make the object itself unavailable. It's just as if you were saying "now this doesn't point anywhere anymore". Hence, it doesn't affect the instance, let alone the other variables that are still pointing to it.

In your code, what you did is setting child1 variable to null, while child2 was still pointing to your instance. Therefore, the code is perfectly valid and doesn't crash. I understand it may be confusing since the field property did change on both child1 and child2, but it really does make sense when you realize they both point to the very same instance. At this point what really was affected wasn't child1 or child2 themselves; it's the field member of the Child instance both were referring to that was.

When no other pointers exists to your object instance, eventually the garbage collector clears it from memory. However, as long as something points to it and that pointer remains within scope, the instance isn't going anywhere.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top