获取强类型接口方法的名称

我有一个像这个例子的界面:

Interface IRequest{ List GetProfiles(); void SetProfile (Profile p); } 

现在,在一些日志记录组件中,我无法访问实现该接口的对象,但我想使用接口中方法的名称。 我当然可以将它们键入为字符串(将方法名称复制到字符串中),但我想使用强类型,因此我不必保持方法名称和字符串同步。

在伪代码中,我会这样做:

 string s= IRequest.GetProfiles.ToString() 

这有可能吗?

编辑:

也许我应该调用它:使用接口,就像它是一个Enum字符串s = IRequest.GetProfiles.ToString()

您可以通过两种方式实现这一目标:

 //If you CAN access the instance var instance = new YourClass(); //instance of class implementing the interface var interfaces = instance.GetType().GetInterfaces(); //Otherwise get the type of the class var classType = typeof(YourClass); //Get Type of the class implementing the interface var interfaces = classType.GetInterfaces() 

然后:

 foreach(Type iface in interfaces) { var methods = iface.GetMethods(); foreach(MethodInfo method in methods) { var methodName = method.Name; } } 

有时您事先不知道class级名称,那么您可以使用:

 var interfaceType = typeof(InterfaceName); var methods = interfaceType.GetMethods(); 

然后:

 List methodNames = new List(); foreach(var method in methods) { methodNames.Add(method.Name); } 

请务必检查方法是否为null并且至少包含一个元素。

你的问题有点难以理解。 我想你想记录实例类或方法的名称……

如果你想要强打字,我认为你需要使用reflection。 你当然可以为每个可以记录的类添加一个字符串名称,但这是一个脆弱的代码,以后有人会讨厌它。 你会用不容易支持reflection的语言看到这种风格,但我建议用C#这样的语言来反对。

那么问一个解决方案:您的日志记录方法是从实例内部调用的吗? 如果是这样,我们可以使用reflection来获取调用方法的名称和许多其他信息。

如果是的话,那么这样的事可能适合你:

 class MyRequest: IRequest { // other interface implementation details omitted public void SetProfiles(Profile p) { if(HasUglyPicture(p)) { MyLogger.LogError(String.Format( "User {0} update attempted with ugly picture", p.UserName) throw new Exception("Profile update failed due to ugly picture!"); } } class MyLogger : ILogger { // other logger details omitted public void LogError(string errorMsg) { // here's where you get the method name // http://www.csharp-examples.net/reflection-calling-method-name/ StackTrace stackTrace = new StackTrace(); MyLogOutputStream.Write(stackTrace.GetFrame(1).GetMethod().Name); MyLogOutputStream.WriteLine(errorMsg); } } 

这个堆栈溢出问题可能会有所帮助: 如何在C#中获取调用方法

该网站包含两个重要行所基于的代码片段: http : //www.csharp-examples.net/reflection-calling-method-name/

这是我取得的最好成绩,HTH:

 using System; using System.Collections.Generic; using System.Runtime.Remoting.Messaging; using System.Runtime.Remoting.Proxies; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace DotNetSandbox { // Subject interface to get names from interface IRequest { List GetProfiles(); void SetProfile(object p); } // Use case / Example: [TestClass] public class InterfaceNamesTests { [TestMethod] public void InterfaceNamesTest() { // Option 1 - Not strongly typed string name = typeof(IRequest).GetMethod("GetProfiles").Name; Console.WriteLine(name); // OUTPUT: GetProfiles // Option 2 - Strongly typed!! var @interface = InterfaceNames.Create(); Func> func = @interface.GetProfiles; var name1 = func.Method.Name; Console.WriteLine(name1); // OUTPUT: GetProfiles Action action = @interface.SetProfile; var name2 = action.Method.Name; Console.WriteLine(name2); // OUTPUT: SetProfile // Other options results with complex/unclear code. } } // Helper class public class InterfaceNames : RealProxy { private InterfaceNames() : base(typeof(T)) { } public static T Create() { return (T)new InterfaceNames().GetTransparentProxy(); } public override IMessage Invoke(IMessage msg) { return null; } } }