2008-08-07 30 views
11

Tôi đang tạo mẫu một số bộ lọc thu thập C# 3 và đã xem xét điều này. Tôi có một bộ sưu tập các sản phẩm:Khi nào sử dụng một phương pháp mở rộng với lambda trên LINQtoObjects để lọc một bộ sưu tập?

public class MyProduct 
{ 
    public string Name { get; set; } 
    public Double Price { get; set; } 
    public string Description { get; set; } 
} 

var MyProducts = new List<MyProduct> 
{    
    new MyProduct 
    { 
     Name = "Surfboard", 
     Price = 144.99, 
     Description = "Most important thing you will ever own." 
    }, 
    new MyProduct 
    { 
     Name = "Leash", 
     Price = 29.28, 
     Description = "Keep important things close to you." 
    } 
    , 
    new MyProduct 
    { 
     Name = "Sun Screen", 
     Price = 15.88, 
     Description = "1000 SPF! Who Could ask for more?" 
    } 
}; 

Bây giờ nếu tôi sử dụng LINQ để lọc nó hoạt động như mong đợi:

var d = (from mp in MyProducts 
      where mp.Price < 50d 
      select mp); 

Và nếu tôi sử dụng ở đâu phương pháp khuyến nông kết hợp với một Lambda bộ lọc hoạt động như tốt:

var f = MyProducts.Where(mp => mp.Price < 50d).ToList(); 

Câu hỏi: sự khác biệt là gì và tại sao sử dụng một trong khác không?

Trả lời

5

LINQ chuyển thành cuộc gọi phương thức giống như mã bạn có.

Nói cách khác, sẽ không có sự khác biệt.

Tuy nhiên, trong hai đoạn mã bạn không gọi .ToList ở đầu tiên, do đó, đoạn mã đầu tiên sẽ tạo ra nguồn dữ liệu đầy đủ, nhưng nếu bạn gọi .ToList trên đó, cả hai phải giống nhau .

0

Ngoài sự khác biệt ToList, # 2 là rất nhiều dễ đọc hơn và tự nhiên IMO

4

Như đã đề cập d sẽ IEnumerable<MyProduct> trong khi f là List<MyProduct>

Việc chuyển đổi được thực hiện bởi các biên dịch C#

var d = 
    from mp in MyProducts 
    where mp.Price < 50d 
    select mp; 

Được chuyển đổi thành (trước khi biên soạn thành IL và với generics được mở rộng):

var d = 
    MyProducts. 
    Where<MyProduct>(mp => mp.Price < 50d). 
    Select<MyProduct>(mp => mp); 
    //note that this last select is optimised out if it makes no change 

Lưu ý rằng trong trường hợp đơn giản này, nó tạo ra sự khác biệt nhỏ. Nơi Linq trở nên thực sự có giá trị là trong vòng lặp phức tạp hơn nhiều. Ví dụ:

Ví dụ: tuyên bố này có thể bao gồm nhóm, đơn đặt hàng và một vài câu lệnh và vẫn có thể đọc được ở định dạng LINQ khi tương đương .Method().Method.Method() sẽ trở nên phức tạp.

0

Cú pháp bạn đang sử dụng cho d sẽ được chuyển đổi bởi trình biên dịch sang cùng IL như các phương pháp mở rộng. Cú pháp "giống SQL" được cho là một cách tự nhiên hơn để biểu diễn một biểu thức LINQ (mặc dù cá nhân tôi thích các phương thức mở rộng). Như đã được chỉ ra, ví dụ đầu tiên sẽ trả về kết quả IEnumerable trong khi ví dụ thứ hai sẽ trả về kết quả Danh sách do cuộc gọi đến ToList(). Nếu bạn loại bỏ cuộc gọi ToList() trong ví dụ thứ hai, cả hai sẽ trả về cùng một kết quả như khi trả về kết quả IEnumerable.

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