2010-08-17 50 views
6

Đây là ứng dụng C# winforms.Làm cách nào để lưu trữ tham chiếu đến thuộc tính đối tượng trong đối tượng khác?

Lời nói đầu:

tôi đang tạo ra một hình thức mà sẽ cho phép người dùng nhập dữ liệu từ một cơ sở dữ liệu máy chủ MySQL hoặc SQL hiện có vào cơ sở dữ liệu SQL Server của tôi. Điều này cho phép người dùng nhanh chóng nhập địa chỉ IP và dữ liệu khác mà không phải nhập lại thông qua điều khiển.

Ví dụ:

giản, tôi có hai đối tượng, FieldObjectSensorObject. FieldObject tồn tại để lưu trữ tên và loại trường cơ sở dữ liệu nguồn và đích. SensorObject là đối tượng mà tôi sau này điền từ các bản ghi trong cơ sở dữ liệu. Vì mục đích đơn giản, tôi bỏ qua việc xử lý kiểu và các chức năng khác không liên quan đến câu hỏi. (Các dữ liệu cho DestinationField được giới hạn trong một danh sách mà tôi cung cấp cho người sử dụng, và xuất phát từ một mảng hoặc danh sách trong chương trình.) Dưới đây là một ví dụ về cả hai:

public class FieldObject 
{ 
    public string DestinationField {get; set;} 
    public string SourceField {get; set;} 
} 

public class SensorObject 
{ 
    public string Name {get; set;} 
    public string IPAddress {get; set;} 
} 

Vấn đề:

Khi người dùng điền vào các trường khác nhau của FieldObject, tôi sử dụng thông tin để điền cơ sở dữ liệu đích, mặc dù tôi có một tuyên bố chuyển đổi lớn để kiểm tra tên trường đích để biết thuộc tính của SensorObject thuộc về nó.

Ví dụ:

// Reader is a SqlDataReader with the prerequisite database connection 
FieldObject myField = new FieldObject 
    { 
     DestinationField = "name", 
     SourceField = "proprietary" 
    }; 
SensorObject mySensor = new SensorObject(); 
switch (myField.DestinationField) 
{ 
    case "name": 
     mySensor.Name = Convert.ToString(Reader[myField.DestinationField]); 
     break; 
    case "ip_address": 
     mySensor.IPAddress = Convert.ToString(Reader[myField.DestinationField]); 
     break; 
} 

Như bạn có thể nhìn thấy nó sẽ đòi hỏi mã dư thừa hơn để xử lý nhiều thuộc tính cho đối tượng.

Câu hỏi:

Tôi muốn một số cách để lưu trữ các tài sản của SensorObject rằng các dữ liệu thuộc về, để khi lặp FieldObjects trong một danh sách, tôi có thể vô hiệu hóa các câu lệnh switch.

Cái gì như:

foreach(FieldObject f in myFieldList) 
{ 
    mySensor(f.mySensorField) = Convert.ToString(Reader[f.DestinationField]); 
} 

Tôi không chắc chắn những gì kỹ thuật trong C# vay chính nó để loại ứng dụng này. Tôi đã xem xét các giá trị tham chiếu và phản chiếu, và dường như không phù hợp.

Tôi đánh giá cao mọi thông tin chi tiết và lời khuyên hoặc thậm chí là cách suy nghĩ lại cách tiếp cận này.

+0

Bạn có thể sử dụng ORM để giải quyết vấn đề này để bạn không phải viết mã dự phòng này không? –

+0

Ánh xạ đối tượng đối tượng? Tôi nghi ngờ nếu tôi không phải tra cứu "ORM" là gì, tôi có thể sử dụng nó. :) Xin lỗi, vẫn là người mới làm quen với hầu hết điều này! – JYelton

+0

Nhìn vào NHibernate: http://nhforge.org/wikis/howtonh/your-first-nhibernate-based-application.aspx trong các ORM dài hạn lấy đi phần lớn nỗi đau khi làm việc với các cơ sở dữ liệu quan hệ, tuy nhiên chúng đòi hỏi một số công việc để bắt đầu. – Zebi

Trả lời

2

Bạn phải sử dụng phản chiếu để thực hiện việc này. nên kết thúc như là một cái gì đó như:

var sensorFields = typeof(SensorObject).GetProperties() 
foreach(var field in fields) 
{ 
    var info = sensorFields.First(sensorField => sensorField.Name == field.Name); 
    var value = Convert.ToString(Reader[field.Destination]); 
    info.SetValue(sensorObj, value, new object[0]); 
} 

GetProperties nhận được một thông tin thuộc tính cho mỗi tài sản có thể được sử dụng để thiết lập giá trị.

Thông tin thuộc tính khóa học có thể được lưu trong bộ nhớ cache.Chỉ cần viết nó một lần và refactor ngay sau khi nó chạy. Đừng quá phức tạp quá nhiều điều này được gọi là tối ưu hóa sớm và dẫn thẳng đến địa ngục;)

+0

Điều này có vẻ rất hữu ích, nó giúp để có một người hiểu phản ánh và sử dụng nó để chỉ đúng hướng! – JYelton

+0

Nếu bạn thay thế nội dung vòng lặp bằng 'lookup.Add (field.Name, field)', trong đó 'lookup' là một' Dictionary ', đó là tất cả những gì bạn cần để lưu các kết quả này cho sau này. –

+0

Tôi không rõ ràng về những gì 'Reader [myField.DestinationField]' là, nhưng tôi không chắc chắn bạn cần phải chuyển đổi nó thành chuỗi. Hoặc, nếu bạn đã làm, tôi sẽ nghĩ rằng bạn chỉ cần gọi 'x.ToString()' thay vì sử dụng 'Convert.ToString (x)'. –

1

Thực ra, phản ánh không phải là ý tưởng tồi, đặc biệt nếu bạn điền từ điển với PropertyInfo trường hợp cho mỗi tên thuộc tính.

1

Bạn có thể làm điều đó với sự phản ánh. Bạn nhận được PropertyInfo của proprty với tên được đề cập, lấy MethodInfo của setter, và sau đó gọi nó.

Có thể mặc dù, có thể lưu trữ một mảng kết hợp (Từ điển hoặc HastTable, v.v.) của các giá trị được lưu trữ theo tên, điều này sẽ dễ xử lý hơn nếu phù hợp.

+1

Nó có thể có ý nghĩa để gọi 'GetSetMethod' trên' PropertyInfo', trả về 'MethodInfo 'cho chính setter. –

+0

@Steven, đúng vậy. Tôi đã quên khi đối tượng được cập nhật mà trong câu hỏi của thời gian tôi đã bắt đầu trả lời :) Cố định, cảm ơn. –

+1

Chỉ cần sử dụng PropertyInfo.SetValue (Object, Object, Object []) – Zebi

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