Late Binding: Revisited (και γιατί πρέπει να μας νοιάζει)

Έχουν δημοσιευτεί 15 Φεβρουαρίου 08 09:56 πμ | KelMan 

Σε συνέχεια του post περί late binding, ας δούμε πως μπορούμε να πετύχουμε σωστό late binding, χωρίς να καταφύγουμε στο quick-and-dirty Option Strict Off.

H μαγική λέξη είναι "Reflection". Τι είναι το Reflection μέσα σε 10'': Είναι ένας μηχανισμός που επιτρέπει την αναζήτηση πληροφοριών σχετικές με μια κλάση κατά το runtime. Δηλαδή, μπορούμε κατά το runtime να βρούμε τι members έχει μια κλάση, τι παραμέτρους δέχονται και τι τιμές επιστρέφουν. Αυτό είναι εξαιρετικά χρήσιμο! Είναι ο μηχανισμός πάνω στον οποίο βασίζεται τo Intellisence και τώρα θα τον χρησιμοποιήσουμε για late binding.

Ας ορίσουμε μια κλάση:

Class TestClass
    Public Function DoSomething(ByVal value As Integer) As Integer
        Return value * 2
    End Function
End Class

Και τώρα ας δούμε πώς θα τη χρησιμοποιήσουμε:

        Dim objTest As New TestClass
        Dim myType As Type
        Dim param(0) As Object
        Dim rslt As Integer

        Dim parameter As String = 5
        Dim functionName As String = "DoSomething"

        param(0) = CType(parameter, Integer)



myType = objTest.GetType rslt = CType(myType.InvokeMember(functionName, _ Reflection.BindingFlags.Default Or _ Reflection.BindingFlags.InvokeMethod, _ Nothing, objTest, param), Integer) Console.WriteLine(rslt)

 

Στην πρώτη ομάδα Dim ορίζουμε το object που θα χρησιμοποιήσουμε, και το array από παραμέτρους που θα περάσουμε ως όρισμα στη μέθοδο που θα καλέσουμε. Στη δεύτερη ομάδα Dim ορίζουμε το όνομα της μεθόδου και τις τιμές των παραμέτρων. Κατόπιν με την GetType διαβάζουμε πληροφορίες της κλάσης που ορίσαμε από το manifest. Τι είναι το manifest σε 20'': Πρόκειται για ένα σύνολο από πληροφορίες που εμπεριέχονται σε κάθε assembly (assembly ονομάζεται στο .NET το παραγόμενο αποτέλεσμα του compilation - το dll ή το exe) που αφορά στην περιγραφή του ίδιου του assembly, πχ όνομα του assembly, έκδοση, culture και - αυτό που μας ενδιαφέρει -type reference πληροφορίες).

Οπότε ερχόμαστε και στο ζουμί:

Πάνω στο myType μπορούμε να καλέσουμε την InvokeMember η οποία (όπως και λέει το όνομά της) θα κάνει την κλήση βάσει των ορισμάτων: Το πρώτο είναι το όνομα της μεθόδου. Το δεύτερο, τα BindingFlags, καθοδηγούν το CLR στο πώς θα κάνει το binding. To τρίτο ορίζει το binder. Με το Nothing αφήνουμε το default binder (με custom binders έχουμε επιπρόσθετο έλεγχο κατά την επιλογή της μεθόδου κατά το Invoke). Με την τέταρτη παράμετρο ορίζουμε το πραγματικό object που θα χρησιμοποιηθεί και με την τελευταία περνάμε τις παραμέτρους της μεθόδου. Γενικά, ο κώδικας παραπάνω είναι απλουστευμένος με την έννοια ότι ξέρουμε ήδη ότι η μέθοδος μας επιστρέφει έναν ακέραιο. Στην πραγματικότητα, θα μπορούσαμε να πάρουμε κι αυτή τη πληροφορία μέσω Reflection.

Φυσικά, όλα τα παραπάνω παίζουν και στη C# δηλαδή η διαφορά που έχει η VB με τη C# στο late binding είναι ο πρώτος τρόπος που είδαμε στο προηγούμενο post. Αυτός ο τρόπος είναι by file late binding καθώς καθορίζεται με το Option Strict setting που είναι per file. Από την άλλη μεριά έχει το πλεονέκτημα ότι καθιστά την VB.NET ένα ιδανικό εργαλείο για εφαρμογές office automation και γενικότερα COM interop καθώς απλουστεύει κατά πολύ το implementation (αρκεί να ξέρει κανείς τι κάνει, αυτό που λέμε Static Typing Where Possible, Dynamic Typing When Needed)

To late binding παρότι ως θέμα είναι παλιό, αποτελεί ένα βασικό μηχανισμό ώστε η VB και η C# να αποκτήσουν dynamic χαρακτηριστικά και γι αυτό τώρα αποκτά νέα δυναμική (pun intended). Στην τωρινή μορφή με χρήση Reflection δεν είναι και τόσο εύκολη διαδικασία και γι αυτό ήδη το team της C# σκέφτεται το πως θα ενσωματώσει το late binding στη γλώσσα. Όπως και να έχει, ένα πράγμα είναι σίγουρο: οι εξελίξεις στις γλώσσες του .NET Framework θα είναι συνεχείς και πολύ ενδιαφέρουσες. Αν μπορούσαμε να στρβλώσουμε και τον χρόνο για να βγάλω 30 ώρες στο 24ωρο, θα ήταν ακόμα καλύτερα.

Δημοσίευση στην κατηγορία:

Σχόλια:

Χωρίς Σχόλια
Έχει απενεργοποιηθεί η προσθήκη σχολίων από ανώνυμα μέλη

Search

Go

Συνδρομές