首页 > 解决方案 > C# 通过引用分配属性

问题描述

可以说我有以下类结构:

public class NewClass
{
    public string Name{get;set;}
    public Int Age{get;set;}
}

public class ChildClass
{
     public List<NewClass> NewClassList {get;set;} 
     //SomeOther properties
}

public class ParentClass
{
     public List<NewClass> NewClassList {get;set;}
     public List<ChildClass> ChildClassList {get;set;}           
}

我的目标是ChildClass.NewClassList参考价值ParentClass.NewClassList

我想这样做是因为 Child 类的每个实例都需要访问 保存的信息ParentClass.NewClassList,但ParentClass.ChildClassList可能是一个非常大的列表,所以我不想保存副本 - 我希望它引用保存的值。

另外,如果我这样做:

var firstParent = new ParentClass
{
    ChildClassList = new List<ChildClass> {//lots of entries},
    NewClassList  = new List<NewClass>()
}

然后,在我的代码中,我想为它分配一个值,firstParent.NewClassList并希望它自动填充子列表中的所有值。

我希望这一切都清楚了吗?

编辑:我已经编辑NewClassList为初始化,但它没有更新子引用,因此我假设它不是通过引用分配的?

标签: c#objectreference

解决方案


您的自定义类NewClassList<T>都是引用类型。

来自微软关于 Reference Types 的文档

C#中有两种类型:引用类型和值类型。引用类型的变量存储对其数据(对象)的引用,而值类型的变量直接包含它们的数据。使用引用类型,两个变量可以引用同一个对象;因此,对一个变量的操作会影响另一个变量引用的对象。对于值类型,每个变量都有自己的数据副本,对一个变量的操作不可能影响另一个变量(除了 in、ref 和 out 参数变量的情况;参见 in、ref 和 out 参数修饰符)。

[强调我的]

因此,要完成您想要做的所有事情,您只需将每个孩子的NewClassList财产分配给其父母的NewClassList.

var firstParent = new ParentClass
{
    NewClassList = new List<NewClass>(),
    ChildClassList = new List<ChildClass>()
};
firstParent.ChildClassList.Add(new ChildClass
{
    NewClassList = firstParent.NewClassList
});
firstParent.ChildClassList.Add(new ChildClass
{
    NewClassList = firstParent.NewClassList
});
firstParent.NewClassList.Add(new NewClass
{
    Name = "Hugh Mann",
    Age = 48
});
//firstParent and both children now contain Hugh Mann.

firstParent.ChildClassList[0].NewClassList.Add(new NewClass
{
    Name = "Sillius Soddus",
    Age = 43
});
//firstParent and both children now contain Sillius Soddus.
    
firstParent.ChildClassList[1].NewClassList.Add(new NewClass
{
    Name = "Joanna Dance",
    Age = 62
});
//firstParent and both children now contain Joanna Dance.
    
firstParent.NewClassList[0].Age = 23;
//Hugh Mann now has an age of 23 in firstParent and its children

如果您要为父级或子级分配不同的列表,他们将不再引用相同的列表。一个列表的更改不会发生在另一个列表上,因为它们引用了完全不同的列表。

var firstParent = new ParentClass
{
    NewClassList = new List<NewClass>(),
    ChildClassList = new List<ChildClass>()
};
firstParent.ChildClassList.Add(new ChildClass
{
    NewClassList = firstParent.NewClassList
});
    
firstParent.ChildClassList[0].NewClassList.Add(new NewClass
{
    Name = "Sillius Soddus",
    Age = 43
});
//firstParent and its child now contain Sillius Soddus.
    
firstParent.NewClassList = new List<NewClass>
{
    new NewClass
    {
        Name = "Hugh Mann",
        Age = 22
    }
};
//firstParent.NewClassList now references a totally different list. It contains Hugh Mann, while firstParent.ChildClassList[0] contains Sillius Soddus.
    
firstParent.NewClassList.Add(new NewClass
{
    Name = "Ian D. Dark",
    Age = 33
});
//firstParent.NewClassList now contains Hugh Mann and Ian D. Dark. Since firstParent.ChildClassList[0] references a totally different list it still only contains Sillius Soddus.

推荐阅读