Only parameterless constructors and initializers a

2020-01-24 20:48发布

I have this error in this linq expression :

var naleznosci = (from nalTmp in db.Naleznosci
                              where nalTmp.idDziecko == idDziec
                              select new Payments
                              (
                                  nalTmp.Dziecko.Imie,
                                  nalTmp.Dziecko.Nazwisko,
                                  nalTmp.Miesiace.Nazwa,
                                  nalTmp.Kwota,
                                  nalTmp.RodzajeOplat.NazwaRodzajuOplaty,
                                  nalTmp.RodzajeOplat.TypyOplat.NazwaTypuOplaty,
                                  nalTmp.DataRozliczenia,
                                  nalTmp.TerminPlatnosci
                              )).ToList();

Any idea how solve this problem? I try with any combination of expression... :/

13条回答
够拽才男人
2楼-- · 2020-01-24 21:05

First I would avoid the solution with

from ....
select new Payments
{
  Imie = nalTmp.Dziecko.Imie,
  ....
}

This requires an empty constructor and ignores encapsulation so you are saying new Payments() is a valid payment without any data, but instead the object must have at least a value and probably other required fields depending on your domain.

It's better to have a constructor for required fields but only bring needed data:

from ....
select new
{
  Imie = nalTmp.Dziecko.Imie,
  Nazwisko = nalTmp.Dziecko.Nazwisko
  ....
}
.ToList() // Here comes transfer to LINQ to Collections.
.Select(nalImp => new Payments
 (
  nalTmp.Imie,//assume this is a required field
  ...........
  )
  {
     Nazwisko = nalTmp.Nazwisko //optional field
  })
.ToList();
查看更多
看我几分像从前
3楼-- · 2020-01-24 21:07

Although it is late to answer, it could still help someone in distress. Since LINQ to entities do not support the parameter-less object constructions. However, the projection methods for IEnumerable.

So prior to selection, just convert your IQueryable to IEnumerable by using this code:

var result = myContext.SomeModelClass.AsEnumerable().Select(m => m.ToString());

It will work fine. However, it will, of course, loose the benefits of native queries.

查看更多
戒情不戒烟
4楼-- · 2020-01-24 21:10

If you still want to use your constructor for initialization and not properties (sometimes this behaviour is desired for initialization purposes), enumerate the query by calling ToList() or ToArray(), and then use Select(…). Thus it will use LINQ to Collections and that limitation of not being able to call constructor with parameters in Select(…) will vanish.

So your code should look something like this:

var naleznosci = db.Naleznosci
                          .Where(nalTmp => nalTmp.idDziecko == idDziec)
                          .ToList() // Here comes transfer to LINQ to Collections.
                          .Select(nalImp => new Payments
                              (
                                  nalTmp.Dziecko.Imie,
                                  nalTmp.Dziecko.Nazwisko,
                                  nalTmp.Miesiace.Nazwa,
                                  nalTmp.Kwota,
                                  nalTmp.RodzajeOplat.NazwaRodzajuOplaty,
                                  nalTmp.RodzajeOplat.TypyOplat.NazwaTypuOplaty,
                                  nalTmp.DataRozliczenia,
                                  nalTmp.TerminPlatnosci
                              ))
                          .ToList();
查看更多
疯言疯语
5楼-- · 2020-01-24 21:12

yeh, try it like this....

var naleznosci = (from nalTmp in db.Naleznosci
                              where nalTmp.idDziecko == idDziec
                              select new Payments()
                              {
                                  Dziecko.Imie,
                                  Dziecko.Nazwisko,
                                  Miesiace.Nazwa,
                                  Kwota,
                                  RodzajeOplat.NazwaRodzajuOplaty,
                                  RodzajeOplat.TypyOplat.NazwaTypuOplaty,
                                  DataRozliczenia,
                                  TerminPlatnosci
                              }).ToList();

this will new up your Payment object using a parameterless constructor, and then initialize the properties that are listed inside the curly braces { }

查看更多
SAY GOODBYE
6楼-- · 2020-01-24 21:17

Having just encountered this error myself, I thought I would add that if the Payment type is a struct, you would also encounter the same error because struct types do not support parameterless constructors.

In that event, converting Payment to a class and using the object initializer syntax will resolve the issue.

查看更多
聊天终结者
7楼-- · 2020-01-24 21:17

Just ToList() the DbSet before the Select statement.. the actual DbSet is saved as a query, it's not fulfilled yet. After calling ToList() you're playing with objects, and then you can use a non-default constructor in the query.

Not the most efficient way usage-time wise, but it's an option on small sets.

查看更多
登录 后发表回答