寻找一种使用实体框架4进行投射的方法

时间:2018-01-04 08:52:51

标签: c# .net linq entity-framework-4

由于新的要求,我们必须将相同的翻译添加到当前开发中,构建在Entity-Framework 4中,并且它使用SQL Server。因此,如果我们有警报,例如,我们需要通过检查翻译某些值(例如标题或描述)来提供数据。

表:

警报

  • AlertId int
  • AlertTypeId int
  • AlertTextEnum int

翻译

  • FieldId int
  • FieldName字符串
  • 代码字符串
  • 描述字符串
  • LanguageId int

因此,如果我们想要获取AlertType的文本,我们必须连接两个表并与Translation.FieldName ==“AlertTypeEnum”和Translation.Code == Alert.AlertTypeEnum建立关系。主要是这样的。

这里我的脏方法在LinqPad上检查但不适用于此版本的Entity-Framework,因为我无法使用ToString方法。

var o = Translations.Where(m => m.LanguageId == 1 && new List<string> {
                        "AlertTypeId"
                    }.Contains(m.FieldName));

 var list = from item in Alerts
            itemTranslation in  o item.AlertTypeId.ToString() equals itemTranslation.Code
                                    into ps
                                    from itemTranslation in ps.DefaultIfEmpty()             
            select new 
            {
                             AlertId = item.AlertId , 
                             AlertTypeDescr = itemTranslation.Description
            }.ToList();

因为这不起作用,我试图在第一个查询之前引入并将Code解析为整数,但它也不起作用。

var o = Translations.Where(m => m.LanguageId == 1 && new List<string> {
                    "AlertTypeId"
                }.Contains(m.FieldName)).
                Select (x => new {
                   Code = (int)( x.Code),
                   FieldName = x.FieldName,
                   Description = x.Description
                }).ToList();

var list = from item in Alerts
                         join itemTranslation in  o
                              on   item.AlertTypeId equals itemTranslation.Code 
                         select new 
                         {
                                       AlertId = item.AlertId , 
                                 AlertTypeDescr = itemTranslation.Description
   };

我得到“无法将类型'字符串'转换为'int'”。

一些建议?我无法更改实体框架和模型的版本。

1 个答案:

答案 0 :(得分:0)

Linq to Entities正在将您的查询转换为SQL脚本,并且没有将字符串转换为int的equilevant。如果我没有弄错的话,string中的intSqlFunctions没有投标方法。所以,我认为你应该改变你的方法并检索数据而不需要原始的任何转换/转换操作。对查询性能也会更好。

您可以在内存中执行强制转换操作,然后可以在属性级别强制转换。

另外,我建议您使用已知类型而不是匿名类型来选择它们。

所以,创建一个类;

public class TranslationModel
{

    public int Code
    {
        get
        {
            //Parse string
            if (!int.TryParse(CodeStr, out var val))
            {
                val = -1;
            }
            return val;
        }
    }

    public string CodeStr { get; set; }

    public string FieldName { get; set; }

    public string Description { get; set; }
}

更改您的查询;

var filterList = new List<string>{ "AlertTypeId" };
var o = Translations.Where(m => m.LanguageId == 1 && filterList.Contains(m.FieldName))
    .Select(x => new TranslationModel
    {
        CodeStr = x.Code,
        FieldName = x.FieldName,
        Description = x.Description
    }).ToList();

最后,您可以在int中使用Code Code TransactionModel属性{/ 1}}形式。