是否可以首先使用代码将数据库计算值映射到“忽略”属性

时间:2012-01-29 23:07:55

标签: entity-framework-4.1 ef-code-first geospatial

看到EF并不完全支持SQL空间数据类型,我希望暂时解决它。 虽然我首先使用代码,但我有一个使用sql2008 r2空间数据类型范围公式的存储过程。我的目标是返回每个对象到查询位置的距离。

在下面的答案的帮助下,我已将我的代码修改为以下

我有一个简单的课程'空缺'

public class Vacancy
{
    public int Id { get; set; }
    public string Title { get; set; }
}

public class VacancyWithRange : Vacancy
{
    public int Calculated { get; set; }
}

然后我直接在像这样的方法中查询上下文

    public List<Vacancy> Get()
    {
        Context db = new Context();

        var context = ((System.Data.Entity.Infrastructure.IObjectContextAdapter)(db)).ObjectContext;

        db.Database.Connection.Open();

        DbCommand cmd = db.Database.Connection.CreateCommand();
        cmd.CommandText = "select *, [Calculated distance from query to vacancy object] as Calculated from Vacancies";
        cmd.CommandType = System.Data.CommandType.Text;

        var result = context.Translate<VacancyWithRange>(cmd.ExecuteReader()).ToList();

        foreach (VacancyWithRange v in result)
        {
            db.Vacancies.Attach(v);
        }
        return result;
    }

Get()方法结束时的foreach循环成功地将VacancyWithRange附加到Vacancies,因此我可以通过延迟加载访问相关对象。

据我所知,这似乎是一个可行的解决方案,目前首先从代码中获取“自定义”计算数据。

感谢阅读。

2 个答案:

答案 0 :(得分:1)

我没有尝试过,但我希望它不起作用。原因是Vacancy是映射实体,一旦您尝试Translate将结果查询到映射实体,EF将使用定义的映射进行转换。问题出现了:在映射中,您指定Calculated属性未映射,因此映射不会填充此属性。

您可以尝试定义一个未映射的新类型,并包含您的Calculated属性(您也可以尝试从Vacancy派生自定义类型,只需添加计算属性)。然后你可以尝试使用:

using (Context db = new Context()) 
{
    string queryText = "select *, [Some random calculated value] as Calculated from Vacancies";
    var data = db.Database.SqlQuery<VacancyWithCalculation>(queryText);
}

新类型中的属性的名称和类型必须与结果集中的列的名称和类型匹配,因为没有显式映射。 EF仅通过按名称匹配结果集列和类属性来使用约定。

顺便说一下。上下文是一次性的,所以不要忘记释放它。

答案 1 :(得分:0)

您应在地图DatabaseGeneratedOption.Computed中指定,即使用HasDatabaseGeneratedOption方法。