如何获取调用我的方法的类名?

时间:2018-02-01 19:44:26

标签: c#

我想写自己的记录器。

这是我的记录管理员:

public static class LoggerManager
{
    public static void Error(string name)
    {

    }
}

我正在调用Error(string name);方法,如下所示:

public class Foo
{
    public void Test()
    {
        LoggerManager.Error(this.GetType().FullName);
    }
}

通过这种方式,我在名为Error的方法中调整了调用者类的名称。

但我不想每次都将名称传递给error方法。我想让我的记录器(或其他记录器方法:Info()Warn())方法单独获取名称。

感谢您的最佳实践......

3 个答案:

答案 0 :(得分:3)

您可以使用CallerMemberNameCallerFilePath属性

public static void Log(string text, [CallerMemberName] string caller = "", [CallerFilePath] string file = "")
{
   WriteLog(text, caller, file);
}


Log("Something happened");

另见CallerLineNumber

BTW:您可能希望将昂贵的 StackFrame 的速度与内置属性进行比较。

int num = 500000;
var t1 = Measure(() => NameOfCallingClass(), num); //<-- 9000
var t2 = Measure(() => Log("aa"), num); //<--26


long Measure(Action func, int num)
{
    func();
    var sw = Stopwatch.StartNew();
    for (int i = 0; i < num; i++)
    {
        func();
    }
    return sw.ElapsedMilliseconds;
}

答案 1 :(得分:1)

您可以使用System.Diagnostics的StackFrame和System.Reflection的MethodBase。

StackFrame(Int32, Boolean)初始化StackFrame类的新实例,该实例对应于当前堆栈帧上方的帧,可选择捕获源信息。

MethodBase,提供有关方法和构造函数的信息。

public static string NameOfCallingClass()
{
    string fullName;
    Type declaringType;
    int skipFrames = 2;
    do
    {
        MethodBase method = new StackFrame(skipFrames, false).GetMethod();
        declaringType = method.DeclaringType;
        if (declaringType == null)
        {
            return method.Name;
        }
        skipFrames++;
        fullName = declaringType.FullName;
    }
    while (declaringType.Module.Name.Equals("mscorlib.dll", StringComparison.OrdinalIgnoreCase));

    return fullName;
}

您的记录器类调用此方法:

public static void Error()
{
    string name = NameOfCallingClass();
}

答案 2 :(得分:-1)

您可以从StackTrace实例中获取它。

public static class LoggerManager
{
    public static void Error()
    {
        var methodInfo = new StackTrace().GetFrame(1).GetMethod();
        var clasName = methodInfo.ReflectedType.Name;
    }
}