【发布时间】:2009-01-07 14:43:37
【问题描述】:
我想知道的是是否有可能(例如)遍历堆栈帧,检查每个调用对象以查看是否与接口匹配,如果匹配则从中提取一些数据。
是的,我知道这是不好的做法,我想知道这是否可能。
【问题讨论】:
标签: c# reflection
我想知道的是是否有可能(例如)遍历堆栈帧,检查每个调用对象以查看是否与接口匹配,如果匹配则从中提取一些数据。
是的,我知道这是不好的做法,我想知道这是否可能。
【问题讨论】:
标签: c# reflection
不,没有 - 至少在不使用某种描述的分析/调试 API 的情况下不会。您可以遍历堆栈以找到调用 方法,但需要注意的是它真的很慢并且由于 JIT 优化可能不准确。这不会告诉你调用 object 是什么(如果确实有的话)。
【讨论】:
如果你想得到类型你可以试试这个:
new StackFrame(1).GetMethod().DeclaringType
正如 Jon 指出的那样,如果您遇到 JIT 优化可能会出现问题。
至于从对象中获取数据,我认为是不可能的。
只是为了详细说明优化问题,取以下代码:
class stackTest
{
public void Test()
{
StackFrame sFrame = new StackFrame(1);
if (sFrame == null)
{
Console.WriteLine("sFrame is null");
return;
}
var method = sFrame.GetMethod();
if (method == null)
{
Console.WriteLine("method is null");
return;
}
Type declaringType = method.DeclaringType;
Console.WriteLine(declaringType.Name);
}
public void Test2()
{
Console.WriteLine(new StackFrame(1).GetMethod().DeclaringType.Name);
}
}
class Program
{
static void Main(string[] args)
{
stackTest s = new stackTest();
s.Test();
Console.WriteLine("Doing Test2");
s.Test2();
Console.ReadLine();
}
}
我们应该两次让 Program 进入控制台,当你在调试器中运行时,你会这样做。当您在发布模式下不使用调试器运行时,您会从第一个 Test 函数获得输出。这可能是因为内联太复杂了,但是,第二种方法会导致空引用异常。
此代码的另一个危险是,在 MS 改进了 JIT 编译器,可能在 2.0 中工作的内容可能会在未来的版本中崩溃和烧毁。
【讨论】:
看到这个问题:
Can you use reflection to find the name of the currently executing method?
这不是重复的,但该问题的答案也会回答您的问题。
【讨论】: