nhibernate是否可以将查询作为IDictionary而不是实体类返回?
我有一个实体人:nhibernate是否可以将查询作为IDictionary而不是实体类返回?,nhibernate,fluent-nhibernate,Nhibernate,Fluent Nhibernate,我有一个实体人: public class Person { public virtual int Id {get; set; } public virtual string FirstName { get; set; } public virtual string MiddleName { get; set; } public virtual string LastName { get; set; } } 使用映射: public class PersonMap {
public class Person
{
public virtual int Id {get; set; }
public virtual string FirstName { get; set; }
public virtual string MiddleName { get; set; }
public virtual string LastName { get; set; }
}
使用映射:
public class PersonMap
{
public PersonMap()
{
Table(TABLE_NAME);
Id( x => x.Id);
Map(x => x.FirstName).Not.Nullable();
Map(x => x.LastName).Not.Nullable();
Map(x => x.MiddleName).Not.Nullable();
}
}
我希望Nhibernate返回字典而不是实体:
IDictionary<string,string> person = session.Get(id);//????
string firstName = person["FirstName"];
IDictionary person=session.Get(id);/????
字符串firstName=person[“firstName”];
这是否可以在不添加其他映射的情况下实现?请查看此博客文章: 如果您想要一个具体的例子,请查看本教程的示例。查看非实体且具有自定义映射逻辑的摘要:
或者在google上搜索只用于此目的的SetResultTransformer,在其他对象或集合中转换结果。包括我的字典 没有,但是您可以通过将逻辑封装在存储库方法中轻松实现这一点
public IDictionary<string, string> GetPersonDictionary(int id)
{
var person = session.Get<Person>(id);
var dict = new Dictionary<string, string>();
dict.Add("FirstName", person.FirstName);
/// etc.
return dict;
}
public-IDictionary GetPersonDictionary(int-id)
{
var person=session.Get(id);
var dict=新字典();
dict.Add(“名字”,person.FirstName);
///等等。
返回命令;
}
您还可以使用反射来填充字典。session.CreateCriteria()
session.CreateCriteria<Person>()
.SetResultTransformer(NHibernate.Transform.Transformers.AliasToEntityMap)
.List<Hashtable>();
.SetResultTransformer(NHibernate.Transform.Transformers.AliasToEntityMap)
.List();
类似这样的事情?您可以通过执行客户端linq投影来实现,请参阅Diego的答案。您需要定义自己的ResultTransformer实现,以使其按您需要的方式工作。下面是一个参考实现,您可以根据需要进行调整。完全缺乏错误检查等;因此,请谨慎使用;)
使用系统;
使用系统集合;
使用NHibernate;
使用NHibernate。性质;
使用NHibernate.Transform;
[可序列化]
公共类字典ResultTransformer:IResultTransformer
{
公共字典ResultTransformer()
{
}
#区域变压器成员
公共IList转换列表(IList集合)
{
回收;
}
公共对象转换元组(对象[]元组,字符串[]别名)
{
var result=newdictionary();
for(int i=0;i
您不需要字典ResultTransformer
,AliasToEntityMapTransformer
做同样的事情,尽管它们都不能单独工作。你会得到一本实体词典
我发现的唯一方法是单独规划每个属性。但是,您不希望手动执行此操作,因为无论何时更改映射,它都会中断。解决方案如下:
var criteria = DetachedCriteria.For<Person>();
criteria.Add(Restrictions.Eq("Id", id));
var projectionList = Projections.ProjectionList();
var metadata = session.SessionFactory.GetClassMetadata(typeof(Person));
foreach (var name in metadata.PropertyNames)
{
projectionList.Add(Projections.Property(name), name);
}
criteria
.SetProjection(projectionList)
.SetResultTransformer(Transformers.AliasToEntityMap);
var result = criteria.GetExecutableCriteria(session)
.UniqueResult<IDictionary>()
var-criteria=DetachedCriteria.For();
标准。添加(限制。等式(“Id”,Id));
var projectionList=Projections.projectionList();
var metadata=session.SessionFactory.GetClassMetadata(typeof(Person));
foreach(metadata.PropertyNames中的变量名)
{
projectionList.Add(Projections.Property(name)、name);
}
标准
.SetProjection(投影列表)
.SetResultTransformer(Transformers.AliasToEntityMap);
var result=criteria.GetExecutableCriteria(会话)
.UniqueResult()
在上面的示例中,我使用一个查询来模拟
Get
。当然,您可以对此稍作更改并返回一个集合;只需调用List
而不是UniqueResult
即可。您能否提供一个使用结果转换器填充字典的示例?我认为不编写自定义的IResultTransformer是不可能的。是的,您必须编写代码。编写干净的代码有时需要更多的努力。这与我想做的非常接近。问题是每个哈希表中都有一个键值对,其中person对象是值。我试图得到一个哈希表,其中每个属性都是一个键值对;但是,我认为不可能使用投影为列名及其值创建KeyValuePair。@Maudite:好的。我明白你的意思了。让我用一个示例result transformer impl发布一个新答案。非常干净的解决方案。杰出的如何从查询中使用它?您可以显示用法吗?@emirhosseini-用法类似于:session.CreateSQLQuery(“从产品p中选择p.Name、p.Price、p.ProductId”).SetResultTransformer(新字典ResultTransformer()).List();
var criteria = DetachedCriteria.For<Person>();
criteria.Add(Restrictions.Eq("Id", id));
var projectionList = Projections.ProjectionList();
var metadata = session.SessionFactory.GetClassMetadata(typeof(Person));
foreach (var name in metadata.PropertyNames)
{
projectionList.Add(Projections.Property(name), name);
}
criteria
.SetProjection(projectionList)
.SetResultTransformer(Transformers.AliasToEntityMap);
var result = criteria.GetExecutableCriteria(session)
.UniqueResult<IDictionary>()