2013-03-28 30 views
5

Tôi cố gắng để chạy sau trong LINQNhận lỗi null LINQ; sau đó không thể sử dụng?

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(); 

Tuy nhiên nhận được một lỗi:

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.

Tôi cố gắng để thêm vào ?? 0; ví dụ rằng:

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; 

Như đã đề cập trong bài viết khác tuy nhiên điều này mang lại một lỗi:

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

Bất kỳ lời đề nghị?

EDIT: mô hình của tôi

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

Có phải 'khoảng cách' không thể sử dụng được không? – mattytommo

+0

Thật không may, tin nhắn sau đó trở thành 'Opperator' ?? ' không thể được áp dụng cho 'đôi' hoặc 'nổi' – NickP

+0

Bạn có thể hiển thị mô hình của mình không? – Alex

Trả lời

2

Bạn nên làm cho bạn khoảng cách nullable gấp đôi trong mô hình của bạn để làm cho ?? công việc. Từ http://msdn.microsoft.com/en-us/library/ms173224.aspx:

?? nhà điều hành được gọi là các nhà điều hành null-coalescing và được sử dụng để xác định một giá trị mặc định cho các loại giá trị nullable hoặc kiểu tham chiếu

Vì vậy, thay đổi mô hình của bạn để

public double? distance { get; set; } 

nên ?? làm việc

+0

Điều đó có thể có tác động (có khả năng rất tiêu cực) đối với bất kỳ điều gì khác sử dụng mô hình. – Stainy

1

quăng tất cả để tăng gấp đôi.

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: cố gắng sử dụng 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

Cùng một vấn đề: 'Opperator' ?? ' không thể được áp dụng cho 'double' hoặc 'float' – NickP

+0

xem chỉnh sửa của tôi, nếu truy vấn của bạn trả về null thì sẽ không có bất kỳ tổng, và tổng sẽ ném ngoại lệ. – Jegan

+0

Nó vẫn không báo lỗi? Giá trị đúc thành giá trị 'Đôi' ​​không thành công do giá trị vật hoá là rỗng. Tham số chung của loại kết quả hoặc truy vấn phải sử dụng một loại nullable. – NickP

-1

Nếu không có quyền truy cập vào phần còn lại của logic của bạn đó là một chút khó khăn để xác định, nhưng tôi sẽ cho nó một đi. Trong khi cá nhân tôi lo lắng hơn về lý do tại sao nó xuất hiện null ngay từ đầu, nếu null là kết quả mong đợi thì bạn có thể sử dụng một kiểu nullable. Bạn có thể tìm thêm thông tin về chúng on MSDN. Nếu bạn sử dụng một kiểu nullable, bạn cũng sẽ muốn kiểm tra giá trị trước khi tiếp tục quá khứ đó dòng totalDistance kép. Điều này được giải thích trong liên kết MSDN.

0

BTW, nếu bất kỳ câu nào trong số này không phải là câu trả lời đúng, chỉ cần cho tôi biết, và tôi sẽ xóa nó. Không cần phải nhận được -1 điên.

Đi theo Linq query with nullable sum

Bạn có thể thử

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; 

Một cách tiếp cận tốt hơn trong tương lai có thể chỉ sử dụng một nullable cho đến khi bạn biết những gì đang xảy ra trong trường hợp có một số ẩn tiềm ẩn ảnh hưởng đến cách biên dịch.EDIT: nó

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; 

Nếu điều đó không làm việc, bạn có thể thử casting để nullables. Hãy nhớ rằng, đây không phải là một diễn viên theo nghĩa đen như một đoạn mã xây dựng một biểu thức LINQ/đối tượng truy vấn có liên quan đến biểu thức truyền và biểu thức truyền phải là để dịch sang thứ gì đó ở phía sau của bạn. Tuy nhiên, tôi không chắc chắn rằng cần phải dịch là phải.

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; 

hoặc

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; 

Và cuối cùng nếu điều đó không làm việc: vít nó. lấy danh sách từ cơ sở dữ liệu, tổng hợp nó với LINQ to Objects (nullable không cần thiết). Chỉ sử dụng như nỗ lực mương cuối cùng. Bạn không nên/không bao giờ phải làm điều này, nhưng có lẽ LINQ dự án của bạn để bất cứ nhà cung cấp chỉ là thực sự kém chất lượng hoặc cũ.

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(); 

Nếu không có cách nào trong số này hoạt động, phải có thứ gì đó vui nhộn khi dịch được tham gia.

Các vấn đề liên quan