Η χύτευση είναι η επεξεργάζομαι, διαδικασία για τη μετατροπή ενός τύπου δεδομένων σε άλλο, για παράδειγμα, από έναν τύπο ακέραιου τύπου σε έναν τύπο στοιχειοσειράς. Μερικές λειτουργίες στο VB.NET απαιτούν να λειτουργούν συγκεκριμένοι τύποι δεδομένων. Η χύτευση δημιουργεί τον τύπο που χρειάζεστε. Το πρώτο άρθρο αυτής της σειράς δύο τμημάτων, Μετατροπές τύπων και τύπων δεδομένων στο VB.NET, εισάγει χύτευση. Αυτό το άρθρο περιγράφει τους τρεις χειριστές που μπορείτε να χρησιμοποιήσετε για να μεταδώσετε VB.NET - DirectCast, CType και TryCast - και συγκρίνει την απόδοσή τους.
Η απόδοση είναι μία από τις μεγάλες διαφορές μεταξύ των τριών φορέων χύτευσης σύμφωνα με τη Microsoft και άλλα άρθρα. Για παράδειγμα, η Microsoft είναι συνήθως προσεκτικός να προειδοποιεί ότι, "DirectCast... μπορεί να προσφέρει κάπως καλύτερη απόδοση από την CType κατά τη μετατροπή από και προς τον τύπο δεδομένων Object. "(Η έμφαση προστέθηκε.)
Αποφάσισα να γράψω κάποιο κώδικα για έλεγχο.
Αλλά πρώτα μια λέξη της προσοχής. Dan Appleman, ένας από τους ιδρυτές του τεχνικού εκδότη βιβλίων Apress και μια αξιόπιστη τεχνική γκουρού, μου είπε κάποτε ότι η απόδοση της συγκριτικής αξιολόγησης είναι πολύ πιο δύσκολο να γίνει σωστά από τους περισσότερους ανθρώπους συνειδητοποιώ. Υπάρχουν παράγοντες όπως η απόδοση της μηχανής, άλλες διαδικασίες που μπορεί να εκτελούνται παράλληλα, βελτιστοποίηση όπως η προσωρινή αποθήκευση μνήμης ή η βελτιστοποίηση του μεταγλωττιστή, καθώς και λάθη στις υποθέσεις σας σχετικά με το τι είναι στην πραγματικότητα ο κώδικας πράξη. Σε αυτά τα σημεία αναφοράς, προσπάθησα να εξαλείψω τα σφάλματα σύγκρισης "μήλων και πορτοκαλιών" και όλες οι δοκιμές εκτελέστηκαν με την έκδοση έκδοσης. Αλλά εξακολουθούν να υπάρχουν σφάλματα στα αποτελέσματα αυτά. Εάν παρατηρήσετε κάποια, ενημερώστε μας.
Οι τρεις χειριστές χύτευσης είναι:
- DirectCast
- CType
- TryCast
Στην πράξη, συνήθως θα διαπιστώσετε ότι οι απαιτήσεις της αίτησής σας θα καθορίσουν ποιο χειριστή χρησιμοποιείτε. Το DirectCast και το TryCast έχουν πολύ περιορισμένες απαιτήσεις. Όταν χρησιμοποιείτε το DirectCast, ο τύπος πρέπει να είναι ήδη γνωστός. Αν και ο κώδικας ...
theString = DirectCast (τοObject, String)
... θα μεταγλωττίσει επιτυχώς εάν το TheObject δεν είναι ήδη μια συμβολοσειρά, τότε ο κώδικας θα ρίξει μια εξαίρεση κατά την εκτέλεση.
Το TryCast είναι ακόμα πιο περιοριστικό επειδή δεν θα λειτουργήσει καθόλου σε τύπους "αξίας" όπως το Integer. (Η συμβολοσειρά είναι ένας τύπος αναφοράς. Για περισσότερα σχετικά με τους τύπους τιμών και τους τύπους αναφοράς, δείτε το πρώτο άρθρο αυτής της σειράς.) Αυτός ο κώδικας ...
theInteger = TryCast (τοObject, ακέραιος αριθμός)
... δεν θα καταρτίσει καν.
Το TryCast είναι χρήσιμο όταν δεν είστε σίγουροι για το είδος του αντικειμένου με τον οποίο εργάζεστε. Αντί να ρίχνει ένα σφάλμα όπως το DirectCast, ο TryCast απλώς επιστρέφει τίποτα. Η συνήθης πρακτική είναι να δοκιμάσετε τίποτα μετά την εκτέλεση του TryCast.
Μόνο το CType (και οι άλλοι χειριστές "Convert" όπως το CInt και το CBool) θα μετατρέψουν τύπους που δεν έχουν σχέση κληρονομιάς, όπως ακέραιο σε μια συμβολοσειρά:
DimString ως String = "1" Dim theInteger ως ακέραιο. theInteger = CType (ηΣτίδα, Ακέραιος)
Αυτό λειτουργεί επειδή το CType χρησιμοποιεί "βοηθητικές λειτουργίες" που δεν είναι μέρος του .NET CLR (Common Language Runtime) για την εκτέλεση αυτών των μετατροπών.
Αλλά θυμηθείτε ότι το CType θα κάνει επίσης μια εξαίρεση εάν το String δεν περιέχει κάτι που μπορεί να μετατραπεί σε ακέραιο. Αν υπάρχει πιθανότητα ότι η συμβολοσειρά δεν είναι ακέραιος όπως αυτή ...
DimString ως String = "George"
... τότε δεν θα λειτουργήσει κανένας χειριστής χύτευσης. Ακόμα και το TryCast δεν θα λειτουργήσει με το Integer επειδή είναι ένας τύπος τιμής. Σε μια περίπτωση όπως αυτή, θα πρέπει να χρησιμοποιήσετε τον έλεγχο ισχύος, όπως ο χειριστής TypeOf, για να ελέγξετε τα δεδομένα σας πριν προσπαθήσετε να τα μεταδώσετε.
Η τεκμηρίωση της Microsoft για το DirectCast αναφέρει συγκεκριμένα τη μετάδοση με έναν τύπο αντικειμένου, γι 'αυτό χρησιμοποιήσαμε στην πρώτη δοκιμή απόδοσης. Η δοκιμή αρχίζει στην επόμενη σελίδα!
Το DirectCast συνήθως χρησιμοποιεί έναν τύπο αντικειμένου, γι 'αυτό χρησιμοποίησα στην πρώτη μου δοκιμή απόδοσης. Για να συμπεριλάβω το TryCast στη δοκιμή, συμπεριέλαβα επίσης ένα μπλοκ if από το γεγονός ότι σχεδόν όλα τα προγράμματα που χρησιμοποιούν το TryCast θα έχουν ένα. Σε αυτή την περίπτωση, ωστόσο, δεν θα εκτελεστεί ποτέ.
Εδώ είναι ο κώδικας που συγκρίνει και τα τρία όταν μεταδίδει ένα αντικείμενο σε μια συμβολοσειρά:
Διόρθωση του χρόνου ως νέου χρονόμετρου () DimString ως συμβολοσειρά. DimTheObject ως αντικείμενο = "Ένα αντικείμενο" Δημιουργία αντιγράφων ως ακέραιος = CInt (Iterations. Κείμενο) * 1000000. ' 'Δοκιμή DirectCast. Η ωρα. Αρχή() Για i = 0 Για τιςΑντιδράσεις. theString = DirectCast (τοObject, String) Επόμενο. Η ωρα. Να σταματήσει() DirectCastTime. Text = Η ωρα. Έχουν περάσει εκατομμύρια δευτερόλεπτα. ToString. ' 'CType Test. Η ωρα. Επανεκκίνηση() Για i ως ακέραιος = 0 για τις απεικονίσεις. theString = CType (τοObject, String) Επόμενο. Η ωρα. Να σταματήσει() CTypeTime. Text = Η ωρα. Έχουν περάσει εκατομμύρια δευτερόλεπτα. ToString. ' 'Δοκιμή TryCast. Η ωρα. Επανεκκίνηση() Για i ως ακέραιος = 0 για τις απεικονίσεις. theString = TryCast (τοObject, String) Αν η Γραμμή δεν Τίποτα Τότε. MsgBox ("Αυτό δεν πρέπει ποτέ να εμφανίζεται") Τέλος εαν. Επόμενο. Η ωρα. Να σταματήσει() TryCastTime. Text = Η ωρα. Έχουν περάσει εκατομμύρια δευτερόλεπτα. ToString.
Αυτή η αρχική δοκιμή φαίνεται να δείχνει ότι η Microsoft έχει σωστό στόχο. Εδώ είναι το αποτέλεσμα. (Τα πειράματα με μεγαλύτερους και μικρότερους αριθμούς επαναλήψεων καθώς και επαναλαμβανόμενες δοκιμές υπό διαφορετικές συνθήκες δεν παρουσίασαν σημαντικές διαφορές από αυτό το αποτέλεσμα.)
Κάντε κλικ εδώ για να εμφανίσετε την εικόνα
Τα DirectCast και TryCast ήταν παρόμοια στα 323 και 356 χιλιοστά του δευτερολέπτου, αλλά η CType πήρε τρεις φορές περισσότερο χρόνο στα 1018 χιλιοστά του δευτερολέπτου. Όταν μεταφέρετε τύπους αναφοράς όπως αυτό, πληρώνετε για την ευελιξία του CType στην απόδοση.
Αλλά λειτουργεί πάντα με αυτόν τον τρόπο; Το παράδειγμα της Microsoft στη σελίδα τους για το DirectCast είναι κυρίως χρήσιμο για να σας ενημερώσουμε συνηθισμένος εργασία με το DirectCast, όχι τι θα κάνει. Ακολουθεί το παράδειγμα της Microsoft:
Dim q Ως Object = 2.37. Dim i ως ακέραιος = CType (q, ακέραιος) 'Η ακόλουθη μετατροπή αποτυγχάνει κατά την εκτέλεση του χρόνου. Dim j Ως ακέραιο = DirectCast (q, ακέραιος) Dim f Ως νέο σύστημα. Windows. Έντυπα. Μορφή. Dim c ως σύστημα. Windows. Έντυπα. Ελεγχος. Msgstr "Η ακόλουθη μετατροπή είναι επιτυχής. c = DirectCast (f, System. Windows. Έντυπα. Ελεγχος)
Με άλλα λόγια, εσείς κλίση χρησιμοποιήστε το DirectCast (ή το TryCast, αν και δεν το αναφέρουμε εδώ) για να μεταδώσετε έναν τύπο Object σε έναν τύπο Integer, αλλά εσείς μπορώ χρησιμοποιήστε το DirectCast για να μεταδώσετε έναν τύπο φόρμας σε έναν τύπο ελέγχου.
Ας ελέγξουμε την απόδοση του παραδείγματος της Microsoft για το τι θα εργασία με το DirectCast. Χρησιμοποιώντας το ίδιο πρότυπο κώδικα που εμφανίζεται παραπάνω, αντικαταστήστε ...
c = DirectCast (f, System. Windows. Έντυπα. Ελεγχος)
... στον κώδικα μαζί με παρόμοιες υποκαταστάσεις για CType και TryCast. Τα αποτελέσματα είναι λίγο περίεργα.
Κάντε κλικ εδώ για να εμφανίσετε την εικόνα
Το DirectCast ήταν στην πραγματικότητα η πιο αργή από τις τρεις επιλογές σε 145 χιλιοστά του δευτερολέπτου. Το CType είναι λίγο πιο γρήγορα σε 127 χιλιοστά του δευτερολέπτου, αλλά το TryCast, συμπεριλαμβανομένου ενός μπλοκ If, είναι το ταχύτερο σε 77 χιλιοστά του δευτερολέπτου. Προσπάθησα επίσης να γράψω τα δικά μου αντικείμενα:
Κατηγορία ParentClass... Τέλος κλάσης. ClassClassClass. Κληρονομεί το ParentClass... Τέλος κλάσης.
Έκανα παρόμοια αποτελέσματα. Φαίνεται ότι αν είστε δεν παίρνοντας έναν τύπο Object, είστε καλύτερα δεν χρησιμοποιώντας το DirectCast.