Como dice el título: ¿Puede la reflexión darle el nombre del método que se está ejecutando actualmente?
Me inclino a adivinar que no, debido al problema de Heisenberg. ¿Cómo se llama a un método que le dirá el método actual sin cambiar cuál es el método actual? Pero espero que alguien pueda probar que estoy equivocado allí.
Actualizar:
- Parte 2: ¿Podría usarse esto para buscar también dentro del código de una propiedad?
- Parte 3: ¿Cómo sería la actuación?
Resultado final
Aprendí sobre MethodBase.GetCurrentMethod (). También aprendí que no solo puedo crear un seguimiento de pila, sino que también puedo crear el marco exacto que necesito si lo deseo.
Para usar esto dentro de una propiedad, simplemente tome una .Substring (4) para eliminar 'set_' o 'get_'.
.net
reflection
Joel Coehoorn
fuente
fuente
Respuestas:
A partir de .NET 4.5 también puede usar [CallerMemberName]
Ejemplo: un establecedor de propiedades (para responder a la parte 2):
El compilador proporcionará literales de cadena coincidentes en los sitios de llamadas, por lo que básicamente no hay sobrecarga de rendimiento.
fuente
StackFrame(1)
método descrito en otras respuestas para el registro, que parecía funcionar hasta que Jitter decidió comenzar a incluir cosas. No quería agregar el atributo para evitar la alineación por razones de rendimiento. El uso del[CallerMemberName]
enfoque solucionó el problema. ¡Gracias!OnPropertyChanged("SomeProperty")
y noOnPropertyChanged("SetProperty")
Para los no
async
métodos, uno puede usarhttps://docs.microsoft.com/en-us/dotnet/api/system.reflection.methodbase.getcurrentmethod
Recuerde que para los
async
métodos devolverá "MoveNext".fuente
async
método probablemente obtendrá "MoveNext" como nombre del método.El fragmento proporcionado por Lex fue un poco largo, así que estoy señalando la parte importante ya que nadie más usó exactamente la misma técnica:
Esto debería devolver resultados idénticos a la técnica MethodBase.GetCurrentMethod (). Name , pero aún vale la pena señalarlo porque podría implementar esto una vez en su propio método usando el índice 1 para el método anterior y llamarlo desde varias propiedades diferentes. Además, solo devuelve un marco en lugar de todo el seguimiento de la pila:
También es de una sola línea;)
fuente
Pruebe esto dentro del método Main en un programa de consola vacío:
Salida de consola:
Main
fuente
Sí definitivamente.
Si desea manipular un objeto, en realidad uso una función como esta:
Esta línea:
Recorre el marco de la pila para encontrar el método de llamada y luego usamos la reflexión para obtener los valores de información de parámetros que se le pasan para una función genérica de informe de errores. Para obtener el método actual, simplemente use el marco de pila actual (1) en su lugar.
Como otros han dicho para el nombre de los métodos actuales, también puede usar:
Prefiero caminar por la pila porque si miras internamente ese método, simplemente crea un StackCrawlMark de todos modos. Dirigirme directamente a la Pila me parece más claro
Post 4.5 ahora puede usar [CallerMemberNameAttribute] como parte de los parámetros del método para obtener una cadena del nombre del método; esto puede ayudar en algunos escenarios (pero realmente, por ejemplo, en el ejemplo anterior)
Esto parecía ser principalmente una solución para el soporte INotifyPropertyChanged donde anteriormente había cadenas sucias a lo largo de su código de evento.
fuente
Comparación de formas de obtener el nombre del método: utilizando una construcción de temporización arbitraria en LinqPad:
CÓDIGO
RESULTADOS
reflejo reflejo
stacktrace stacktrace
inlineconstant inlineconstant
constante constante
expr e => e.expr ()
exprmember exprmember
miembro principal
Tenga en cuenta que los métodos
expr
ycallermember
no son del todo "correctos". Y allí verá una repetición de un comentario relacionado de que la reflexión es ~ 15 veces más rápida que stacktrace.fuente
EDITAR: MethodBase es probablemente una mejor manera de obtener el método en el que se encuentra (en lugar de toda la pila de llamadas). Sin embargo, todavía estaría preocupado por la línea.
Puede usar un StackTrace dentro del método:
Y la mirada a los cuadros:
Sin embargo, tenga en cuenta que si el método está en línea, no estará dentro del método que cree que está. Puede usar un atributo para evitar la alineación:
fuente
new StackTrace(true)
lugar denew StackTrace(false)
. Establecer esotrue
hará que el seguimiento de la pila intente capturar el nombre del archivo, el número de línea, etc., lo que podría hacer que esta llamada sea más lenta. De lo contrario, una buena respuestaLa forma simple de tratar es:
Si System.Reflection está incluido en el bloque using:
fuente
¿Qué tal esto esto:
fuente
Creo que deberías poder obtener eso creando un StackTrace . O, como mencionan @ edg y @ Lars Mæhlum , MethodBase. GetCurrentMethod ()
fuente
Prueba esto...
fuente
Acabo de hacer esto con una clase estática simple:
luego en tu código:
fuente
fuente