2008-11-23 34 views
21

Mój scenariusz powinien być prosty ... typ, który chcę przekonwertować OD jest ZAWSZE "ciąg". Co chcę przekonwertować do ... może być wiele rzeczy - ints, DateTimes, ... struny itdJak konwertować typy w środowisku wykonawczym?

To byłoby proste:

string valueToConvertFrom = "123"; 

int blah = Convert.ToInt32(valueToConvertFrom); 

Jednak ... nie wiem (do czasu wykonania), że wartość, którą muszę przekonwertować, to "Int" (lub cokolwiek innego). Próbowałem tego:

string valueToConvertFrom = "123"; 

Type convertToType = typeof(int); 

object blah = Convert.ChangeType(valueToConvertFrom, convertToType); 

Ale to daje mi następujący błąd: "Obiekt musi wdrożyć IConvertible."

Nie chcę, aby wykonać instrukcję zmiany i zadzwonić "Convert.ToBlah" w oparciu o nazwę typu ... wszelkie sugestie?

+0

proszę ponownie otworzyć i dodać odpowiedź, że znalazłeś, w przypadku, ktoś inny ma ten sam lub podobny problem w przyszłości –

+1

Powodem, dla którego to zamknąłem, jest to, że mój kod zawiera błąd ... Początkowo pobierałem dane z niewłaściwego pola, a to pole nie implementowało IConvertible. +1 dla obu odpowiedzi ... "Klasa String implementuje IConvertible, ten kod po prostu POWINI pracować" to prawda. Ale rozwiązanie Ashera jest wspaniałe, ponieważ nauczyłem się czegoś nowego (i jest to bardzo czyste rozwiązanie). Dzięki jeszcze raz! –

Odpowiedz

30

czysty sposób to zrobić za pomocą TypeConverter. można uzyskać wystąpienie konwertera typów, wywołując TypeDescriptor.GetConverter, a następnie przy użyciu instancji konwertera typów, aby wykonać konwersję. więc coś takiego:

string valueToConvertFrom = "123"; 

Type convertToType = typeof(int); 

TypeConverter tc = TypeDescriptor.GetConverter(convertToType);    

object blah =tc.ConvertFromString(valueToConvertFrom); 
+0

To jest genialne. Wielkie dzięki! – Stephen

+2

Odpowiedź Ashera nie dotyczy Silverlight (web lub WP7x), gdzie TypeDescriptor nie jest dostępny. Ponadto TypeDescriptor zwraca tylko TypeConverter dla Type, który zdefiniował TypeConverter, który nie stosuje się automatycznie do większości typów. A TypeConverter zwrócony przez TypeDescriptor jest tylko pierwszym zdefiniowanym dla danego Typu. Więc nie można zasadniczo polegać na TypeDescriptor dla scenariuszy konwersji, delikatnie mówiąc. –

+1

Należy również pamiętać, że TypeConverter jest nie tylko abstrakcyjną klasą bazową wymagającą niestandardowej implementacji, jeśli używa się jej do niestandardowej konwersji klasy, ale jest również relatywnie wolniejsza niż inne mechanizmy, ponieważ opiera się na odbiciu/odkryciu. –

5

Klasy String implementuje IConvertible, ten kod po prostu POWINI pracować. Którą wersją .NET celujesz?

object o = Convert.ChangeType(str, convertToType); 

Poza tym większość typów wspomniałeś wdrożyć metody Parse, więc najlepszym strzał może być coś takiego.

Type convertToType = ...; 
MethodInfo mi = convertToType.GetMethod("Parse", BindingFlags.Static); 
object blah; 
if(mi != null) 
{ 
    blah = mi.Invoke(null, new object[]{valueToConvertFrom}); 
} 
else 
{ 
    // the type doesn't implement the Parse method, handle it another way :/ 
} 
+2

to wygląda i czuje się jak włamywacz ... – Asher

5

pytanie Timothy'ego, stosowany zazwyczaj do kwestii konwersji typu w .NET, jest to bardzo duży problem. Podczas gdy strategie konwersji są dość proste w określonych scenariuszach ze znanymi typami, niestety nie ma uogólnionej strategii w jakiejkolwiek implementacji .NET, aby dokonać konwersji typu w czasie wykonywania z jednego dowolnego typu na inny, ani takiej strategii nie ma w przypadku Redmond. Jednak Microsoft dostarcza kilka dobrych wskazówek dla ogólnej koncepcji typów konwersji, w tym:

miałem do czynienia z tym samym ogólnej emisji w moim i jako rozwiązanie skonsolidowałem wszystkie standardowe strategie w jedną metodę. Zakres tego problemu jest szeroki, a związane z nim strategie konwersji są zróżnicowane, więc to skonsolidowane podejście można opisać wyłącznie w pełnym artykule technicznym. Jednakże, oferuję tutaj kopię dokumentacji mojej metody w nadziei, że pomoże ci to w zrozumieniu ogólnych wymagań, które będziesz musiał rozwiązać, jeśli chcesz opracować podobne, uogólnione rozwiązanie.Oto link do mojego dokumentacji:

Mam nadzieję, że to pomoże Ci się,

Mark

Powiązane problemy