我正在尝试构建一个看起来像这样的对象:
public class MyObject
{
private IList<AnotherObject> items;
public List<AnotherObject> Items
{
return items.AsEnumerable().ToList<AnotherObject>();
}
}
我正在使用NHibernate作为我的DAL并将其直接映射到items字段,所有这些都可以正常工作。
我也使用Windows Workflow,复制器活动不适用于通用IList。 (http://social.msdn.microsoft.com/Forums/en-US/windowsworkflowfoundation/thread/2ca74b60-fd33-4031-be4b-17a79e9afe63)这基本上迫使我使用List&lt;&gt;包装器而不是IList&lt;&gt;。这当然打破了直接NHibernate映射,因为NHibernate的IList实现不能直接转换为List。
**编辑:Windows Workflow要求实际上意味着我将失去对列表的类型安全访问,无论它需要IList。
现在的目标是序列化/反序列化此对象。这适用于二进制序列化,但当我尝试反序列化时,底层NHibernate代理对象会出现nhibernate错误。
所以我尝试了xml序列化。序列化工作正常,并在序列化的xml文件中给出了我很好的具体类定义,它完全剥离了nhibernate代理。但是,在尝试反序列化时,我无法将项目添加到列表中作为items.AsEnumerable.ToList调用将不允许通过.Add方法将项目添加到基础列表。
有没有人对此有任何想法?我是以错误的方式来做这件事的吗?
**编辑:NHibernate具体类是NHibernate.Collection.Generic.PersistentGenericBag,它确实直接实现了IList。但是,我失去了通用列表的所有类型安全的好处。这让我回到必须为每个子对象编写包装器的领域,如果可能的话我真的想避免这种情况。
答案 0 :(得分:2)
On选项是创建自己的CustomList实现,该实现是实现IList
的实例的包装即:
public CustomList<AnotherObject> Items
{
return new CustomList<AnotherObject>(items);
}
即。当您添加到CustomList<T>
时,它会添加到支持列表中。
只要您的班级实施IList
以及IList<T>
,您就可以了。
答案 1 :(得分:1)
是的,不幸的是你不能这样做。调用ToList()
会创建一个全新的列表实例,因此当您向该实例添加项目时,它们不会反映在原始列表中(正如您已经清楚地发现的那样)。
我不使用NHibernate,但我很想知道你的容器是否实现IList
(非通用版本)。从您引用的主题看来,System.Collections.IList
似乎是实际需要的(并且由List<T>
实现,这就是它的工作原理)。您的容器是否实现了IList
?
答案 2 :(得分:0)
难道你不能像这样投这个吗?
public class MyObject
{
private IList<AnotherObject> items;
public List<AnotherObject> Items()
{
return (List<AnotherObject>)items;
}
}
没有机会尝试,但我认为它应该有效!
答案 3 :(得分:0)
我认为NHibernate PersistentBag(非泛型)集合实现了IList
,因此您可以将项目键入IList
而不是IList<AnotherObject>
。您的问题中的链接指出问题是复制器需要IList List<T>
实现但IList<T>
没有(如图)。
答案 4 :(得分:0)
可以转换为IEnumerable&lt; T&gt;?你可以试试这个:
public class MyObject
{
private IList<AnotherObject> items;
public List<AnotherObject> Items
{
return new List<AnotherObject>items.Cast<AnotherObject>());
}
// or, to prevent modifying the list
public IEnumerable<AnotherObject> Items
{
return items.Cast<AnotherObject>();
}
}