实体Famework:在Linq问题中选择日期格式

时间:2016-04-06 18:34:43

标签: c# entity-framework linq lambda

嗨我在控制器中有这个代码,这可以很好地转换 Fecha 属性的日期格式

var com = db.Comentario
               .Where(co => co.IdProducto == id)
               .OrderByDescending(c => c.Fecha)
               .Skip((int)offset)
               .Take(2)
               .ToList()
               .Select(c => new {
                   c.Id,
                   Usuario = new {
                       c.Usuario.Nombre,
                       c.Usuario.Apellidos,
                       c.Usuario.Avatar,
                       c.Usuario.Nickname
                   },
                   c.Contenido,
                   Fecha = c.Fecha.ToShortDateString(), //it works fine
                   R = c.IdEstado == 1 ? false : true
               });

但......问题出在另一个控制器

        db.Comentario.Add(com);
        db.SaveChanges();

        var resp = db.Comentario
                .Where(c => c.Id == com.Id)
                .Select(c => new {
                    c.Id,
                    Usuario = new {
                        c.Usuario.Nombre,
                        c.Usuario.Apellidos,
                        c.Usuario.Avatar,
                        c.Usuario.Nickname
                    },
                    c.Contenido,
                    Fecha = c.Fecha.ToShortDateString(),//the problem is here
                    R = c.IdEstado == 1 ? false : true
                }).FirstOrDefault();

这里我向数据库插入一个 Comentario 对象,我希望在JSON结果中返回该对象,但是出现了这个错误

  

LINQ to Entities无法识别方法'System.String ToShortDateString()'方法,并且此方法无法转换为商店表达式。

我无法理解代码失败的原因,如果两者都是相同的代码。 感谢

2 个答案:

答案 0 :(得分:1)

它们不一样......只要调用.ToList(),就会对底层数据存储执行查询。

var com = db.Comentario
               .Where(co => co.IdProducto == id)
               .OrderByDescending(c => c.Fecha)
               .Skip((int)offset)
               .Take(2)
               .ToList() // <<< Your query is being executed here

上面的所有内容都很容易被EntityFramework翻译成SQL ...实体框架为您检索数据,在您调用ToList()之后,数据存储在内存中,这意味着数据已被检索并且您'不再查询存储在数据库中的数据,而是查询已经获取的数据。

将它与你的第二个例子进行比较......

    var resp = db.Comentario
            .Where(c => c.Id == com.Id)
            .Select(c => new {   // <<< Here you're still querying the
                c.Id,            //     database, nothing has been received / executed yet.
                Usuario = new {
                    c.Usuario.Nombre,
                    c.Usuario.Apellidos,
                    c.Usuario.Avatar,
                    c.Usuario.Nickname
                },
                c.Contenido,
                Fecha = c.Fecha.ToShortDateString(),

EntityFramework尚未获取数据,它正在尝试将您的查询转换为SQL,但您无法将ToShortDateString()转换为SQL。您需要做的就是在ToList()Where(...)条款之间使用Select(...)执行您之前完成的查询。

答案 1 :(得分:0)

好消息的人,我找到了解决方案,买我不确定这是不是最好的方式。

      var resp = db.Comentario
                .Include(u=>u.Usuario) // with this Usuario is no longer null
                .Where(c => c.Id == com.Id && c.IdEstado != 3)
                .ToList()
                .Select(c => new {
                    c.Id,
                    Usuario = new {
                        c.Usuario.Nombre,
                        c.Usuario.Apellidos,
                        c.Usuario.Avatar,
                        c.Usuario.Nickname
                    },
                    c.Contenido,
                    Fecha = c.Fecha.ToShortDateString(),
                    R = c.IdEstado == 1 ? false : true
                });

我删除了 FirstOrDefault(),并在Where和Select子句之间添加 ToList()

这是我的解决方案 谢谢:D