2010-07-29 34 views
9

Tôi là một mô hình khung thực thể (v.1.0) mà tôi đang cố gắng mở rộng với một thuộc tính được tính toán.Thực thể Khung tính chất vấn đề tài sản

tôi đã tạo ra lớp một phần để mở rộng đối tượng thực thể "Offer" theo cách này:

namespace MyModelNamespace 
{ 
    public partial class Offer 
    { 
     public bool MyProperty 
     { 
      get 
      { 
       // my stuffs the return true or false 
      } 
     } 
    } 
} 

Nó biên dịch mà không vấn đề trong lắp ráp của tôi, nhưng khi chạy, khi tôi đang cố gắng để làm điều gì đó như thế này:

_myEntities.OfferSet.FirstOrDefault(o=>o.MyProperty); 

tôi lấy lỗi này:

The number of members in the conceptual type 'MyModelNamespace.Offer' does not match with the number of members on the object side type 'MyModelNamespace.Offer'. Make sure the number of members are the same.

... bất cứ đề nghị ???

Trả lời

5

Có, bạn có thể thực hiện việc này. Sử dụng LINQ translations library.

+0

thú vị ... Tôi sẽ cố gắng càng sớm càng tốt! – tanathos

+2

Tôi đang thử nó, nhưng tôi không thể làm cho nó hoạt động: (... Tôi đã bao gồm dll, và nó biên dịch tốt, nhưng trong thời gian chạy tôi nhận được một cái gì đó như: "Thành viên được chỉ định 'MyProperty' không được hỗ trợ bởi LINQ to Entities. "Tôi đã theo dõi chính xác các ví dụ trong liên kết bạn đã đăng. – tanathos

+0

@tanathos Vấn đề của bạn có thể liên quan đến việc khởi tạo tĩnh. Xem nhận xét của Matyas Boros từ ngày 30 tháng 8 trên bài viết đó.Cách giải quyết được đề xuất ở đây là tạo một hàm tạo tĩnh (trống) trên lớp, và sau đó khởi tạo một thể hiện của đối tượng đó trước khi nó được truy vấn. Ugly :( – AaronSieb

1

Bạn không thể đẩy thuộc tính tùy chỉnh xuống cơ sở dữ liệu. Bạn nên có một cái gì đó giống như

"The specified type member 'MyProperty' is not supported in LINQ to Entities. Only initializers, entity members, and entity navigation properties are supported."

Cách duy nhất để thực hiện những gì bạn muốn là đưa nó vào bộ nhớ. Và sau đó lọc.

_myEntities.OfferSet.ToList().FirstOrDefault(o=>o.MyProperty); 

Tôi đoán có lẽ đây là cách tốt hơn để thực hiện những gì bạn đang làm.

EDIT Tôi đồng ý Craig có một cách khác, giả sử * nó có thể được dịch thành biểu thức cửa hàng. Nếu bạn đang ánh xạ thuộc tính cho một số loại truy vấn, bạn sẽ có thể tìm kiếm/đẩy bộ lọc xuống.

+0

Không phải cách duy nhất; xem câu trả lời của tôi –

+0

Bạn là chính xác, tôi đã giả định ông đã cố gắng sử dụng một số loại tài sản liên tục hoặc có nguồn gốc. – Nix

+0

'AsEnumerable()' tốt hơn 'ToList()' trong trường hợp này. –

0

Một cách bạn có thể thử là sử dụng không gian tên System.Linq.Expressions và phương pháp mở rộng AsExpandable có sẵn here.

Tôi nghĩ bạn có thể chuyển biểu thức sang phương thức FirstOrDefault và nếu bạn vẫn muốn sử dụng MyProperty ở nơi khác, bạn có thể sử dụng cùng một biểu thức để tính giá trị của nó. Vì vậy, bạn muốn có một cái gì đó như:

public partial class Offer 
{ 
    public static Expression<Func<Offer, bool>> exp 
    { 
     get 
     { 
      return o => o.Property1 * o.Property2 == someValue; 
     } 
    } 

    public bool MyProperty 
    { 
     get 
     { 
      return exp.Compile()(this); 
     } 
    } 
} 

Rồi sau này, bạn vượt qua nó trong:

_myEntities.OfferSet.AsExpandable().FirstOrDefault(Offer.exp.Compile())); 

Nếu tính của bạn có thể được chuyển đổi thành một cây biểu thức SQL hiểu, tôi nghĩ rằng điều này sẽ làm việc . Nó làm việc với một lớp thử nghiệm không thực thể, nhưng sử dụng nó với LINQ to Entities là một động vật khác.

Tôi đã không sử dụng nhiều AsExpandable, vì vậy mã này có thể không đúng. Tôi mở cửa để sửa chữa.

+0

'MyFunc' sẽ cần phải là một' Expression

+0

Điểm tốt. Điều này có nghĩa là lambda cần phải là một biểu thức thay thế của một khối lệnh, vì vậy tôi hy vọng việc tính toán có thể được diễn tả theo cách đó. –

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