Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
[This post is part of a series, "wish-list for future versions of VB"]
IDEA: GetType should work on instances.
' Currently we can get the System.Type of a named type
Dim t As Type = GetType(IEnumerable(Of ))
' We'd also like to get the compile-time System.Type of a given expression
Dim x As IEnumerable(Of Integer) = {1, 2, 3}
Dim t1 As Type = GetType(x) ' returns IEnumerable(Of Integer), the compile-time type
Dim t2 As Type = x.GetType() ' returns Integer(), the run-time type
' this doesn't evaluate the expression: it merely figures out its compile-time type:
Dim t As Type = GetType(New C)
Dim t As Type = GetType(Me) ' returns the compile-time type of "Me"
Dim t As Type = GetType(MyClass) ' for shared methods, returns the type of the class/module we're in
IDEA: GetType should be able to return stuff about a given method/property, or the current method/property. For instance,
' We'd also like to get the Reflection.MethodInfo of a specified method
Dim m As Reflection.MethodInfo = GetType(AddressOf Console.WriteLine(x))
' The expression isn't evaluated: it's merely used to resolve which overload
Dim m As Reflection.MethodInfo = GetType(AddressOf Call (New C).f(15 * Factorial(2)))
' A common need is to get the name of the current method
Dim m As Reflection.MethodInfo = GetType(AddressOf MyMethod)
' Likewise for properties, events, fields
Dim p As Reflection.PropertyInfo = GetType(AddressOf c.p)
Dim e As Reflection.EventInfo = GetType(AddressOf c.e)
Dim f As Reflection.FieldInfo = GetType(AddressOf c.f)
' And the current property:
Dim m As Reflection.MethodInfo = GetType(AddressOf MyProperty)
This idea has been frequently discussed and requested, e.g. here in Eric Lippert's blog. What has sunk the idea every single time is that getting a decent syntax for the feature is just so hard. One of the big problems with syntax is overloads, as in the Console.WriteLine example above. One approach is to invent a wholly new syntax which lets you write method signatures inside the GetType operator. Another approach, as I've taken here, is to write just a normal invocation expression -- except it's not invoked; it's merely used as a well-understood syntax for specifying which overload we want.
But all of the above examples can already be implemented today with a fairly decent workaround and recognizable syntax:
Dim minfo = GetMethodInfo(Sub() f())
Dim pinfo = GetPropertyInfo(Function() p)
Dim tinfo = GetTypeInfo(Me)
Dim current_minfo = Reflection.MethodBase.GetCurrentMethod()
Dim current_pinfo = GetPropertyInfo(Reflection.MethodBase.GetCurrentMethod())
Function GetMethodInfo(f As Expressions.Expression(Of Action)) As Reflection.MethodInfo
Return DirectCast(f.Body, Expressions.MethodCallExpression).Method
End Function
Function GetPropertyInfo(Of T)(ByVal f As Expressions.Expression(Of Func(Of T))) As Reflection.MemberInfo
Return DirectCast(f.Body, Expressions.MemberExpression).Member
End Function
Function GetPropertyInfo(ByVal minfo As Reflection.MemberInfo) As Reflection.PropertyInfo
Return (From p In minfo.DeclaringType.GetProperties() Where p.GetAccessors().Contains(minfo)).FirstOrDefault
End Function
Function GetTypeInfo(Of T)(ByVal x As T) As System.Type
Return GetType(T)
End Function
Provisional evaluation from VB team: The current workarounds do everything that's needed, and their syntax is familiar. There doesn't seem need to invent any new syntax for this. If anything, the Power6: __CALLER_MEMBER__ idea was neater than any of these proposals.
Comments
Anonymous
February 15, 2010
The only real requirement I have in this area is to be able to get the name of methods and parameters (as well as types) at compile time – it would make validation / logging SO much easier. The reflection option is not appropriate in these cases as it is too expensive – I can’t risk someone using a slow name lookup on a method which may be evaluated in a tight loop. What I want to be able to do is use the method or parameter name in code and have the comopiler resolve it for maximum runtime efficiency – for example: AssertNonNull(surname, NameOf(surname)) or... Log(“entering method {0}”, NameOf(Method)) Something like this would massively simplify a lot of my validation and logging code.Anonymous
February 15, 2010
The one thing the workarounds really don't address is getting hold of an event at compiled time - currently this is only possible via reflection. Also - it seems to me that the workarounds defer problems to run time and wherever possible, it's better for these things to fail at compile time if possible.Anonymous
February 15, 2010
I like to be able to get Reflection object for Type (already have GetType), Method, Property, Event, Argument, Field (have I forgotten something?). Because we often need only name of such object, special syntax to get name of the object makes sense - and it can be translated to string in compile-time. Also Property/Event delegates may be helpful. Main advantage of having such operators rather than passing string somewhere (Me.GetType.GetProperty("Item")) is that it is compiler-checked and thus refactoring-safe. Making GetType accept expression is not very important for me.Anonymous
March 13, 2010
I like the idea of having a consistent syntax: Knowing that you can type GetType on anything and have it "just work".Anonymous
January 11, 2011
Idea 1 (GetType(reference)) - Good ieda Idea 2 (GetType(method) returns MethodInfo) looks too dangerous to me