请查看以下代码
public class Page
{
public string type { get; set; }
public List<Contains> contains { get; set; }
}
public class Contains
{
public string type { get; set; }
public string index {get; set;}
public List<Contains> contains { get; set; }
}
public class PageMachine
{
Page Page;
List<Contains> PageContainer;
public PageMachine(string type)
{
Events = new Dictionary<string, Events>();
PageContainer = new List<Contains>();
Page = new Page()
{
type = type,
contains = PageContainer
};
}
public void Add_Container(string rootIndex, string type, string index)
{
Contains container = new Contains()
{
type = type,
index = index,
};
SetContainer(rootIndex, index, container, Page.contains);
}
private void SetContainer(string rootIndex, string index, Contains newContainer, List<Contains> containers)
{
if(containers == null)
{
containers = new List<Contains>();
containers.Add(newContainer);
}
else if(containers.Count == 0)
{
containers.Add(newContainer);
}
else if(!containers.Exists(x => x.index == rootIndex))
{
containers.Add(newContainer);
}
else
{
foreach (var container in containers)
{
if (container.index == rootIndex)
{
SetContainer(index, index, newContainer, container.contains);
}
else
{
}
}
}
}
实施
PageMachine page = new PageMachine("My Page");
page.Add_Container("0", "Parent 1", "0");
page.Add_Container("0", "Child 1 of Perant 1", "0.0");
这背后的想法是为页面创建容器列表,每个容器可以包含更多子容器的列表。包含的索引属性用作映射,父级0
,其子级为0.0
,其子级为0.0.0
。
我面临的问题是,当调用递归SetContainer
并且在方法中传递container.contains
时,Page对象并不反映List已更新。
我发现很难解释我的问题,并会澄清是否有问题。
答案 0 :(得分:2)
我相信原因在于
if(containers == null)
{
containers = new List<Contains>();
containers.Add(newContainer);
}
您正在创建一个新的List
,但您认为引用并未指出这一点,因为在通过引用传递参数时(在container.contains
中为SetContainer
),参考是复制。
我试着说明一下。第二次调用SetContainer
(递归),container.contains
指向null。
container.contains --> null
此参数通过引用SetContainer
传递。这意味着该参考已复制。此复制的引用是SerContainer
内使用的引用,换句话说是参数containers
。
container.contains --> null
^
|
containers ------------+
现在,由于containers
为空,因此第一个if
语句为true,并创建一个新的List
,容器指向该值。
container.contains --> null
containers ----------> newList
添加项目时,会将其正确添加到newList,但container.contains
未指向该项目。这就是为什么当SetContainer
返回时,没有任何变化。我希望我已经清楚了。
解决此问题的一种方法是确保在调用SetContainer
之前创建列表,例如将if
循环中的for
语句更改为
if (container.index == rootIndex)
{
if(container.contains == null)
container.contains = new List<Contains>();
SetContainer(index, index, newContainer, container.contains);
}
当然从第一个containers = new List<Contains>();
语句中删除if
。从快速测试来看,它似乎对我有用。
有道理吗?