如何降低C#中方法初始化的成本?
我正在编写一个缓存部分排序结构,以便相同结构的后续搜索能够利用先前的搜索。预计这需要快速处理大型集合(超过100万个项目),因此在基本上一切正常后,我正在尝试对其进行分析 在这样做的过程中,我遇到了下面的方法,它显然——至少在调试编译的代码中——在初始化该方法时使用了大约17%的总执行时间(第一个如何降低C#中方法初始化的成本?,c#,optimization,profiling,C#,Optimization,Profiling,我正在编写一个缓存部分排序结构,以便相同结构的后续搜索能够利用先前的搜索。预计这需要快速处理大型集合(超过100万个项目),因此在基本上一切正常后,我正在尝试对其进行分析 在这样做的过程中,我遇到了下面的方法,它显然——至少在调试编译的代码中——在初始化该方法时使用了大约17%的总执行时间(第一个{字符旁边的17%),这感觉非常多。代码被频繁调用,在发布模式下,我希望它能够内联,但鉴于以下情况,我无法确定实际发生了什么初始化-所有访问和修改的变量都是表示搜索的整体struct中的字段 有谁能指出
{
字符旁边的17%),这感觉非常多。代码被频繁调用,在发布模式下,我希望它能够内联,但鉴于以下情况,我无法确定实际发生了什么初始化-所有访问和修改的变量都是表示搜索的整体struct
中的字段
有谁能指出C#编译器可能需要在下面创建变量来代替语法糖等的地方,或者帮助我理解为什么这个方法的初始化成本与它的执行成本大体相同?(第一个循环大约11%,第二个循环大约4%)
值得注意的是,\u p\u Items\u SortedFlag
是指向布尔数组中第一项的指针,其他所有内容都是int
s
[MethodImpl(MethodImplOptions.AggressiveInlining)]
private void StepBackToUnsorted()
{
// Step the RCursor back to the last unsorted item
// Costs circa 11% on the while conditions.
while (_p_Items_SortedFlag[_RCursor] && _RCursor > _LCursor)
{
--_RCursor;
++_RCount;
}
// Step the Upper Right bound through any sorted
// items
// Costs Circa 4% on the while conditions.
while (_p_Items_SortedFlag[_RUpper] && _RUpper > _RCursor)
--_RUpper;
}
如前所述,这段代码在发布时可能会内联。然而,我仍然非常感兴趣——从how-can-I-avoid-it-when-it-Is-Not-inlined的角度来看——是什么导致了这样一个东西的如此巨大的初始化成本,实际上所有东西都应该在那里等待使用。您尝试过传递构建的代码吗通过反编译器编写代码以查看实际生成的内容?我发现这有时很有用。你是什么意思:_p_Items_SortedFlag是指向布尔数组中第一个项的指针?
_p_Items_SortedFlag
在查看代码时是一个数组。此代码仅在循环中调用,就在我调用之前(bool*p=\u项目\u分类标签){u p_Items\u SortedFlag=p;…
。想法是修复数组的内存一次,然后与使用共享字段相比,减少分配局部变量的开销。大致将我的总体执行时间减少一半。公平地说,我还没有尝试反编译代码。今晚我将通过ILSpy运行它,看看它在做什么……你尝试过passi吗通过反编译器查看构建的代码以查看实际生成的是什么?我发现这有时很有用。你是什么意思:_p_Items_SortedFlag是指向布尔数组中第一个项的指针?_p_Items_SortedFlag
在查看代码时是一个数组。此代码仅在循环中被调用,就在我调用之前(bool*p=\u项目\u分类标签){{u p\u Items\u SortedFlag=p;…
。想法是修复数组的内存一次,然后与使用共享字段相比,减少分配局部变量的开销。大致将我的总体执行时间减少一半。公平地说,我还没有尝试反编译代码。今晚我将通过ILSpy运行它,看看它在做什么。。。