下面是我的问题的演示, 我想创建许多孩子,他们提到了他们的父母。
如何编写import属性以获取父引用而不是创建新的父实例?
public partial class MainPage : UserControl
{
[Import(typeof(Parent))]
public Parent Parent1 { get; set; }
[Import(typeof(Parent))]
public Parent Parent2 { get; set; }
public MainPage()
{
InitializeComponent();
CompositionInitializer.SatisfyImports(this);
Parent1.name = "p1";
Parent2.name = "p2";
}
}
[PartCreationPolicy(CreationPolicy.NonShared)]
[Export(typeof(Parent))]
public class Parent
{
[Import(typeof(Child))]
public Child Child1 { get; set; }
[Import(typeof(Child))]
public Child Child2 { get; set; }
public string name;
}
[PartCreationPolicy(CreationPolicy.NonShared)]
[Export(typeof(Child))]
public class Child
{
//how to write the import attribute
public Parent Parent { get; set; }
public string name;
}
答案 0 :(得分:3)
MEF最适合将单独的模块链接在一起。将一个意味着在同一逻辑层次结构中的对象组合起来有点过分。
我会打扮Child
属性来设置父级:
[PartCreationPolicy(CreationPolicy.NonShared)]
[Export(typeof(Parent))]
public class Parent
{
private Child _child1;
private Child _child2;
[Import(typeof(Child))]
public Child Child1
{
get { return _child1; }
set { _child1 = value; _child1.Parent = this; }
}
[Import(typeof(Child))]
public Child Child2
{
get { return _child2; }
set { _child2 = value; _child2.Parent = this; }
}
public string name;
}
这样,只要满足导入以创建Parent
类的子项,Child
类也将设置Parent
个引用。这种链接引用的方式是MEF友好且非常标准。只是不要在两个方向都这样做(如果你有一对一的关系),因为你会得到一个无限循环。
您似乎在其设计范围之外使用MEF。在MEF中,对于每个合同名称,您可以使用一个单一引用或多个单一类型的引用。 MEF唯一的上下文是合同名称(或合同类型的名称)。
我希望这会有所帮助。
答案 1 :(得分:2)
如果我理解你的问题,你不能在这里进行导入,因为MEF没有你在这里寻找的上下文。我的建议是在Parent上导入Child的Child.Parent属性。也许在Child1 / Child2设置器中只需将Parent属性设置为此。
答案 2 :(得分:0)
你可能会遇到问题,因为MEF中的组合机制是递归的,它会遍历所有要绘制的对象。你在这里做的是试图将一个项目导入另一个项目,另一个项目将尝试导入第一个项目。您将看到的另一个问题是您正在指定NonShared的CreationPolicy,这意味着将为每个导入创建一个新实例。将它与递归问题相结合,就会发生完美的内存/性能灾难;)
我要做的是将Parent的CreationPolicy更改为Shared,这样它就不会再次组合,并且可以通过子项中的Import属性进行分配。不利的一面是,您的Parent1和Parent2属性实际上将是Parent的相同实例。