2009-03-01 24 views
22

Phương pháp mở rộng cho Trình lập chỉ mục, chúng có tốt không?Phương pháp mở rộng cho người lập chỉ mục, liệu chúng có tốt không?

Tôi đang chơi xung quanh với một số mã có thể hydrat hóa POCO.

Mã lặp xung quanh các hàng được trả về từ SqlDataReader và sử dụng sự phản chiếu để gán các thuộc tính từ các giá trị cột. Xuống ngăn xếp cuộc gọi của tôi Tôi đã có một dòng mã như sau: -

poco.Set("Surname", "Smith"); // uses extension method ... 

Phương thức thiết lập được viết dưới dạng phương pháp mở rộng.

Nó sẽ là tuyệt vời để có thể viết mã như thế này

poco["Surname"] = "Smith"; // extension methods for indexers ? 

tức là tôi muốn viết một phương pháp mở rộng cho indexer

Có lý do chính đáng tại sao Net không có phương pháp khuyến nông cho người lập chỉ mục? Những người khác có sử dụng tốt cho các chỉ mục phương pháp mở rộng không?

như một sang một bên ... Nếu chúng ta có thể viết phương pháp khuyến nông cho indexers sau đó chúng ta có thể viết mã như thế này ...

var poco = PocoFactory(); 
    poco.Surname = “Smith”; // is this JavaScript ... 
    poco[Surname] = “Smith” ; // … or is this c# or both 

Một số đoạn từ mã của tôi

///////////////////////////////////////////// 
// Client calling code 
IDab dab = DabFactory.Create("Northwind"); 
string sql = @"select * from Customers "; 
var persons = dab.ExecuteReader<NorthwindCustomer>(sql); 
if (dab != null{ 
    Assert.That(persons[0].CustomerID , Is.EqualTo("ALFKI"));} 
///////////////////////////////////////////// 
List<T> IDab.ExecuteReader<T>(string commandText) 
{ 
    List<T> pocos = new List<T>(); 
    // setup connection 
    SqlDataReader reader = command.ExecuteReader(CommandBehavior.CloseConnection); 
    while (reader.Read()) 
    { 
      Dictionary<string, int> colMappings = null ; 
      if (colMappings == null){ 
       colMappings = reader.GetSqlDataReaderColumnMappings();} 
      T poco = new T(); 
      poco.DbToMem<T>(reader, colMappings); 
      pocos.Add(poco); 
     } 
    } 
    // connection cleanup ... 
    return pocos ; 
} 

// the set extension method signature 
public static void Set<T>(this T thisClientObject, string thisPropertyName, object newValue) where T : class 

Trả lời

11

Indexer chia sẻ rất nhiều của tính phổ biến với các thuộc tính (dưới mui xe, một chỉ mục thuộc tính có chỉ mục) và các thuộc tính tiện ích mở rộng không tồn tại. Đồng ý, sẽ có những tình huống mà chúng tiện dụng.

Làm lại kịch bản được trình bày - theo một số cách, điều này khá giống như dynamic. Tất nhiên, nếu bạn khai báo giao diện một trình chỉ mục chuỗi, thì mã trình đọc của bạn có thể sử dụng trực tiếp - nhưng sẽ là công việc không cần thiết để triển khai giao diện này nhiều lần!

Làm lại phương thức mở rộng; điều này có sử dụng sự phản chiếu thường xuyên không? Bạn có thể muốn xem xét các thủ thuật như HyperDescriptor, điều này có thể tiết kiệm rất nhiều thời gian cho CPU nếu bạn thực hiện rất nhiều thao tác này. Điển hình sử dụng sau đó sẽ là:

PropertyDescriptorCollection props = TypeDescriptor.GetProperties(typeof(T)); 
while (reader.Read()) 
{ 
    T poco = new T(); 
    // abbreviated... 
    (per prop) 
     props[propName].SetValue(poco, cellValue); 
} 

Bạn có thể tối ưu hóa này hơn nữa bằng cách nhìn vào cột trở lại đầu tiên (một lần mỗi lưới, không phải mỗi hàng), và chỉ truy cập vào các cột phù hợp ...

Hoặc cách khác, xem xét các công cụ ORM; Expression cũng có thể được sử dụng để đọc dữ liệu (Tôi có một ví dụ hoàn chỉnh về điều này ở đâu đó trên usenet, cho DbLinq)

+0

cảm ơn thú vị, tôi sẽ xem xét. – judek

-1

Để tái hydrat hóa Pocos, tôi khuyên bạn nên xem gói AutoMapper Nuget. Nó làm cho thực sự đơn giản và làm giảm đáng kể số lượng mã.

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