Il metodo non può essere tradotto in un'espressione negozio


89

Ho visto questo codice funzionare con LINQ to SQL ma quando utilizzo Entity Framework, viene visualizzato questo errore:

LINQ to Entities non riconosce il metodo 'System.Linq.IQueryable'1 [MyProject.Models.CommunityFeatures] GetCommunityFeatures ()' e questo metodo non può essere tradotto in un'espressione del negozio.

Il codice del repository è questo:

public IQueryable<Models.Estate> GetEstates()
{
    return from e in entity.Estates
           let AllCommFeat = GetCommunityFeatures()
           let AllHomeFeat = GetHomeFeatures()
           select new Models.Estate
                      {
                                EstateId = e.EstateId,
                                AllHomeFeatures = new LazyList<HomeFeatures>(AllHomeFeat),
                                AllCommunityFeatures = new LazyList<CommunityFeatures>(AllCommFeat)
                      };
}

public IQueryable<Models.CommunityFeatures> GetCommunityFeatures()
{
    return from f in entity.CommunityFeatures
           select new CommunityFeatures
                      {
                          Name = f.CommunityFeature1,
                          CommunityFeatureId = f.CommunityFeatureId
                      };
}

public IQueryable<Models.HomeFeatures> GetHomeFeatures()
{
    return from f in entity.HomeFeatures
           select new HomeFeatures()
           {
               Name = f.HomeFeature1,
               HomeFeatureId = f.HomeFeatureId
           };
}

LazyList è un elenco che estende la potenza di IQueryable.

Qualcuno potrebbe spiegare perché si verifica questo errore?

Risposte:


115

Motivo: per impostazione predefinita , LINQ to Entities richiede che l'intera espressione di query LINQ venga tradotta in una query del server. Solo poche sottoespressioni non correlate (espressioni nella query che non dipendono dai risultati del server) vengono valutate sul client prima che la query venga tradotta. Le chiamate a metodi arbitrari che non hanno una traduzione nota, come GetHomeFeatures () in questo caso, non sono supportate.
Per essere più specifici, LINQ to Entities supporta solo inizializzatori e costruttori senza parametri . Soluzione: Pertanto, per superare questa eccezione, è necessario unire la query secondaria a quella principale per GetCommunityFeatures () e GetHomeFeatures ()

invece di richiamare direttamente i metodi dall'interno della query LINQ. Inoltre, c'è un problema sulle righe che stavi cercando di creare un'istanza di una nuova istanza di LazyList utilizzando i suoi costruttori parametrizzati, proprio come avresti potuto fare in LINQ to SQL . Per questo la soluzione sarebbe passare alla valutazione client delle query LINQ (LINQ to Objects). Ciò richiederà di richiamare il metodo AsEnumerable per le query LINQ to Entities prima di chiamare il costruttore LazyList.

Qualcosa di simile dovrebbe funzionare:

public IQueryable<Models.Estate> GetEstates()
{
    return from e in entity.Estates.AsEnumerable()
       let AllCommFeat = from f in entity.CommunityFeatures
                         select new CommunityFeatures {
                             Name = f.CommunityFeature1,
                             CommunityFeatureId = f.CommunityFeatureId
                         },
       let AllHomeFeat = from f in entity.HomeFeatures
                         select new HomeFeatures() {
                             Name = f.HomeFeature1,
                             HomeFeatureId = f.HomeFeatureId
                         },
       select new Models.Estate {
            EstateId = e.EstateId,
            AllHomeFeatures = new LazyList<HomeFeatures>(AllHomeFeat),
            AllCommunityFeatures = new LazyList<CommunityFeatures>(AllCommFeat)
       };
}


Ulteriori informazioni: dai un'occhiata a LINQ to Entities, cosa non è supportato? per maggiori informazioni. Controlla anche LINQ to Entities, Soluzioni alternative su ciò che non è supportato per una discussione dettagliata sulle possibili soluzioni. (Entrambi i collegamenti sono le versioni memorizzate nella cache perché il sito Web originale è inattivo)

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.