Maged Algaafary Maged Algaafary - 22 days ago 6
Vb.net Question

Using for each to iterate class properties

I have this class

Public Class TExperience
Public ID As Integer
Public CompanyName As String
Public Country As String
Public Years As Integer
Public Months As Integer
Public JobTitle As String
Public Function Arr() As String()
Return {"ID", "CompanyName", "Country", "Years", "Months", "JobTitle"}
End Function
End Class


and this is how it work

Public Function Set()
Dim D As New TExperience
D.CompanyName = "Any Data"
D.Country = "Any Data"
D.ID = "Any Data"
D.JobTitle = "Any Data"
D.Months = "Any Data"
End Function


I need to exchange this by "For Each....." in class

D.CompanyName = "Any Data"
D.Country = "Any Data"
D.ID = "Any Data"
D.JobTitle = "Any Data"
D.Months = "Any Data"


How to do this?

Answer

Yea, this is possible if...
Note: you posted class with public fields, e.g. Public CompanyName As String. While it is usually good idea to use properties - Public Property CompanyName As String. The code below is for class properties but you can substitute PropertyInfo for FieldInfo. However, it is recommended to use properties to expose class values.

If you're looking for yes/no answer to question, can setting properties via for-each happen?, the answer is yes. But more questions about your question should arise. When, why, what for..., etc.

For example, we have a situation that specific types have common properties with other types, sometimes even deriving from those types and we need to convert them. One way was to use a "Decorator" pattern. But here is what we've done to hydrate properties (disclaimer - code was converted from c# via converter and I added some tings like "as type", I am not sure it is 100% correct)

''' Everything "S" - source, "D" - destination. "T" - type
Public Shared Function Hydrate(Of TS, TD)(source As TS, destination As TD) As TD

    Dim sPI() As PropertyInfo = 
        source.[GetType]().GetProperties(BindingFlags.[Public] Or BindingFlags.Instance)
    Dim dPI() As PropertyInfo = 
        destination.[GetType]().GetProperties(BindingFlags.[Public] Or BindingFlags.Instance)

    For Each s As PropertyInfo In sPI
        Dim d As PropertyInfo = 
            dPI.FirstOrDefault(Function(pi) pi.Name = s.Name AndAlso pi.PropertyType = s.PropertyType)
        If d IsNot Nothing Then
            d.SetValue(destination, s.GetValue(source, Nothing), Nothing)
        End If
    Next
    Return destination
End Function

So, here we go. In this example properties iterated and when their names and data types match exactly, they are populated. But other than hydration of similar models, what is the use of it? I mean, this is what happens internally when JSON being deserialized, etc. But in everyday programming you don't do anything like this.