2013-03-28 7 views
5

Próbuję uruchomić następujące w LINQUzyskiwanie błędu null LINQ; nie możesz wtedy użyć?

double totalDistance = (from g in db.Logs join 
    h in db.Races on g.raceId equals h.RaceId 
    where g.userId == id select h.distance).Sum(); 

Jednakże pojawia się błąd:

The cast to value type 'Double' failed because the materialized value is null. Either the result type's generic parameter or the query must use a nullable type.

Próbowałem dodać na ?? 0; takie, że:

double totalDistance = (from g in db.Logs join 
    h in db.Races on g.raceId equals h.RaceId 
    where g.userId == id select h.distance).Sum() ?? 0; 

Jak sugerowano w innych postach to jednak daje błąd:

operator '??' cannot be applied to operands double or int

jakieś sugestie?

EDIT: mój model

namespace RacePace.Models 
{ 
public class Race 
{ 
    public int RaceId { get; set; } 

    [DisplayName("Race Setting")] 
    public string place { get; set; } 
    [DisplayName("Distance (km)")] 
    public double distance { get; set; } 
    [DisplayName("Date")] 
    public DateTime date { get; set; } 
    [DisplayName("Commencement Time")] 
    public DateTime timeStarted { get; set; } 
    [DisplayName("Active")] 
    public Boolean active { get; set; } 
    [DisplayName("Description")] 
    public string description { get; set; } 
    [DisplayName("Creator")] 
    public int UserId { get; set; } 
} 
} 
+2

Czy 'odległość' jest zerowa? – mattytommo

+0

Niestety, ten sam komunikat staje się "Opperatorem" ?? nie można zastosować do "podwójnego" lub "ruchomych" – NickP

+0

Czy możesz pokazać swój model? – Alex

Odpowiedz

2

Powinieneś zrobić odległość podwójnego zerowania w swoim modelu, aby ?? praca. Od http://msdn.microsoft.com/en-us/library/ms173224.aspx:

The ?? Operator nazywa operator null koalescencyjny i służy do określenia wartości domyślnej dla typów wartości pustych lub typ referencyjny

więc zmiana modelu do

public double? distance { get; set; } 

powinny ?? praca

+0

Może to mieć (potencjalnie bardzo negatywny) wpływ na wszystko, co korzysta z modelu. – Stainy

1

rzucić im wszystko podwoić.

double totalDistance = (double)((from g in db.Logs join h in db.Races on g.raceId equals h.RaceId where g.userId == id select h.distance).Sum() ?? 0); 

Edit: spróbuj użyć double.Parse

var someObject = (from g in db.Logs join h in db.Races on g.raceId equals h.RaceId where g.userId == id select h.distance); 
double totalDistance = (someObject !=null)? someObject.Sum() : 0; 
+0

Ten sam problem: "Opperator" ?? nie można zastosować do "podwójnego" lub "pływającego" – NickP

+0

zobacz moją edycję, jeśli twoja kwerenda zwróci wartość null, wtedy nie będzie żadnej sumy, a suma wyrzuci wyjątek. – Jegan

+0

Nadal nie wyświetla się błąd? Odrzucenie do typu wartości "Double" nie powiodło się, ponieważ zmaterializowana wartość ma wartość NULL. Typowy parametr typu wynikowego lub zapytanie muszą używać typu zerowego. – NickP

-1

Bez dostępu do reszty logiki jest to trochę trudne do określenia, ale dam mu szansę. Podczas gdy ja osobiście bardziej martwiłbym się, dlaczego pojawia się null w pierwszej kolejności, jeśli null jest oczekiwanym rezultatem, wtedy możesz być w stanie użyć typu zerowego. Możesz znaleźć więcej informacji na ich temat on MSDN. Jeśli użyjesz typu zerowego, będziesz także chciał sprawdzić wartość przed kontynuacją tej podwójnej linii totalDistance. Zostało to wyjaśnione w łączu MSDN.

0

BTW, jeśli któraś z nich nie jest właściwą odpowiedzią, po prostu daj mi znać, , a ja to usunę. Nie musisz tracić -1 na punkcie szaleństwa.

Przechodzenie przez Linq query with nullable sum

Można spróbować

double totalDistance = 
    (from g in db.Logs join h in db.Races 
    on g.raceId equals h.RaceId where g.userId == id 
    select h).Sum(x => x.distance) ?? 0; 

Lepszym rozwiązaniem w przyszłości może być tylko używać pustych aż wiesz, co się dzieje na wypadek, gdyby istniała jakaś dziwna, niejawna obsada wpływająca na sposób jej kompilacji.EDIT: robi

double? totalDistanceTemp = 
     (from g in db.Logs join h in db.Races 
     on g.raceId equals h.RaceId where g.userId == id 
     select h).Sum(x => x.distance); 
double totalDistance = totalDistanceTemp ?? 0; 

jeśli to nie pomoże, można spróbować odlewania do nullables. Pamiętaj, że nie jest to dosłowne odlewanie, ponieważ jest to fragment kodu budującego ekspresję LINQ/obiekt, który można przypisać, który obejmuje wyrażenie odlewu, a to wyrażenie powinno być przetłumaczone na coś z twojego końca. Nie jestem jednak pewien, czy konieczne jest przetłumaczenie ,.

double? totalDistanceTemp = 
     (from g in db.Logs join h in db.Races 
     on g.raceId equals h.RaceId where g.userId == id 
     select h).Sum(x => (Double?) x.distance); 
double totalDistance = totalDistanceTemp ?? 0; 

lub

double? totalDistanceTemp = 
     (from g in db.Logs join h in db.Races 
     on g.raceId equals h.RaceId where g.userId == id 
     select ((Double?)h.distance)).Sum(); 
double totalDistance = totalDistanceTemp ?? 0; 

I wreszcie, czy to nie działa: przykręcić. pobierz listę z bazy danych, zsumuj ją z LINQ do Objects (wartość null nie powinna być wymagana). Używaj tylko jako ostatniego wysiłku przy rowu. Nie powinieneś/powinnaś nigdy tego nie robić, ale może twoje projekty LINQ do jakiegokolwiek dostawcy są po prostu tandetne lub stare.

double totalDistance = 
     (from g in db.Logs join h in db.Races 
     on g.raceId equals h.RaceId where g.userId == id 
     select h.distance).AsEnumerable().Sum(); 

Jeśli żadna z tych prac, musi istnieć coś śmiesznego w jaki sposób dołączyć jest tłumaczone, że albo jestem brakujące lub usługodawca robi coś głupi (albo żadne z powyższych, oczywiście).

Powiązane problemy