C# C语言中的内存布局优化#
免责声明:下面的措辞可能有一些误解,如果我误解了wy,请纠正我。我的代码是用C#处理的,从我写代码到看起来像0和1之间 问题如下(已链接): 在C#中,无论我是否使用优化技术,我的数据结构和/或数据操作实现是否会对性能产生影响 编译器在输出IL时做什么,它可靠吗? 意思:如果我把我的数据做成SOA,它会是IL中的SOA吗?总是吗 当JIT读取IL时,我的数据结构会发生什么变化?它变了吗?它是否自动优化以适合我的处理器 cf: 我知道这篇演讲是针对本机代码的,并且讨论了处理器布局与本机代码中的数据布局的具体区别 我还知道C#编译器和JIT编译器会在这些问题上为我优化东西 基本上,我想知道这种优化是否会对我的表现产生影响:C# C语言中的内存布局优化#,c#,performance,memory,optimization,jit,C#,Performance,Memory,Optimization,Jit,免责声明:下面的措辞可能有一些误解,如果我误解了wy,请纠正我。我的代码是用C#处理的,从我写代码到看起来像0和1之间 问题如下(已链接): 在C#中,无论我是否使用优化技术,我的数据结构和/或数据操作实现是否会对性能产生影响 编译器在输出IL时做什么,它可靠吗? 意思:如果我把我的数据做成SOA,它会是IL中的SOA吗?总是吗 当JIT读取IL时,我的数据结构会发生什么变化?它变了吗?它是否自动优化以适合我的处理器 cf: 我知道这篇演讲是针对本机代码的,并且讨论了处理器布局与本机代码中的数据
- SOA代替AOS
- 向量访问模式(在内存中连续访问)
- 等等。。。你说得对
- (如果你认为C语言中的值类型总是在堆栈上,请阅读它,因为你会得到一次款待)
- (更重要的是,这是答案)
按照汉斯的回答再进一步:
当你说:“你可以追求SOA,但那没有帮助。是的,你的程序会因为所有的结构复制而减速,而且是以确定性的方式进行的。但这并不能阻止雨。你会得到两者中最坏的一面,一个缓慢的程序和完全相同的暂停。” 这并不意味着我的程序不会从SOA中获得任何好处—它将更快(潜在地),因为它将有助于处理我的数据。只是它本身不会对GC产生影响
另一件事是,如果我不在数据布局中执行SOA或其他改进,编译器就不会为我改进,对吗?我不能依靠编译器来处理这种事情?担心GC就像担心今天是否会下雨一样。天迟早要下雨,你没办法阻止它。这是必须的,如果不这样做,你就不能让草坪看起来很绿。你永远不想做的就是故意阻止下雨。因为如果你这样做的话,它会像洪水一样倾泻而下,冲走那美丽的草坪。一场稳定的毛毛雨是你想要的。最好是在晚上你不看的时候 NET GC强烈支持这一点。只有较小的第0代和第1代集合将暂停您的程序。昂贵的gen#2收集在代码继续执行时在后台进行。最糟糕的情况是暂停时间大约在100微秒左右。这与您的程序在现代操作系统上暂停的其他原因很难区分。就像你的游戏循环因为另一个更高优先级的内核线程需要运行而被暂停一样。只是一场蒙蒙细雨,肉眼看不见
您可以追求SOA,但这没有帮助。是的,您的程序会因为所有的结构复制而减慢,并且是以确定性的方式进行的。但是雨停不了。这两种情况都是最糟糕的,一个缓慢的程序和完全相同的暂停
别担心下雨,只要确保雨在合适的时间下就行了。要利用背景GCs,您需要对数据进行结构化,使其要么寿命非常短,要么使用gen#0/1集合很容易消失。或者它的寿命很长,所以它会在第二代找到一个舒适的家,并在那里呆上一段时间。这通常是程序中非常常见的模式,尤其是在游戏中。你根本不太可能需要做任何事情。如果你谈论的是这种级别的东西,那么C#(或任何托管内存环境)可能不适合你。但话说回来……你是在从事实时计算、金融计算、大数据等工作吗?实时但C#可以适当地用于提供那种级别的控制,我希望布局没有根本改变。@GéryArduino根据定义,实时和垃圾收集器是互斥的。@Aron你可以在C#中使用一些编程技术,类似于对象池/预分配以避免分配(行话中称为零分配/genzero)。甚至还有。当然,这不再是惯用的C语言了,很难做到正确,它需要广泛的分析,但这确实是可能的。“你可以追求SOA,但那没有帮助”——嗯?我看不出GC会对程序的内存访问模式产生任何影响的任何原因,以及缓存等带来的后续影响。至少对于.NET 4.5(即使使用SustainatedLowlatency模式)来说,没有停止全球GCs的说法是不正确的-它们只是比以前更加罕见。不知道你的评论有什么相关性,请发布您自己的答案。我认为发表评论的一个原因是对答案中发布的事实提出质疑,并要求澄清或更正,而不仅仅是对答案进行否决。感谢Hans给出了这么好的回答,我更新了我的问题,要求澄清。SOA是否更有效还没有定论。这通常不是因为你有太多的A,但唯一确定的方法是测量。您确实可以从jitter(而不是编译器)获得帮助,当它运行时,它会努力使S高效