优化 XNA 上的颜色操作
我正在分析我的简单 2D XNA 游戏。我发现整个运行时间的 4% 是通过将两种 Colors 添加在一起的简单操作占用的,其中一个首先乘以 float 。
我需要每帧调用此方法 2000 次(对于地图上的每个图块),这为 XNA 的 60 fps 提供了每秒 120000 次的调用。即使单个调用的最小提升也会产生巨大的速度影响。但我只是不知道如何才能使其更有效
private void DoColorCalcs(float factor, Color color)
{
int mul = (int)Math.Max(Math.Min(factor * 255.0, 255.0), 0.0);
tile.Color = new Color(
(byte)Math.Min(tile.Color.R + (color.R * mul / 255), 255),
(byte)Math.Min(tile.Color.G + (color.G * mul / 255), 255),
(byte)Math.Min(tile.Color.B + (color.B * mul / 255), 255));
}
编辑:正如 Michael Stum 所建议的:
private void DoColorCalcs(float factor, Color color)
{
factor= (float)Math.Max(factor, 0.0);
tile.Color = new Color(
(byte)Math.Min(tile.Color.R + (color.R * factor), 255),
(byte)Math.Min(tile.Color.G + (color.G * factor), 255),
(byte)Math.Min(tile.Color.B + (color.B * factor), 255));
}
这将时间使用量从 4% 降低到 2.5%
I am profiling my simple 2D XNA game. I found that 4% of entire running time is taken by simple operarion of adding together two Colors , one of them multiplied first by float.
I need to call this method rogulthy 2000 times per frame (for each tile on map), which gave me 120000 times per second for XNA's 60 fps. Even minimal boosting of single call whould give huge speed impact. Yet I simple do not know how can I make this more effective
private void DoColorCalcs(float factor, Color color)
{
int mul = (int)Math.Max(Math.Min(factor * 255.0, 255.0), 0.0);
tile.Color = new Color(
(byte)Math.Min(tile.Color.R + (color.R * mul / 255), 255),
(byte)Math.Min(tile.Color.G + (color.G * mul / 255), 255),
(byte)Math.Min(tile.Color.B + (color.B * mul / 255), 255));
}
EDIT: As suggested by Michael Stum:
private void DoColorCalcs(float factor, Color color)
{
factor= (float)Math.Max(factor, 0.0);
tile.Color = new Color(
(byte)Math.Min(tile.Color.R + (color.R * factor), 255),
(byte)Math.Min(tile.Color.G + (color.G * factor), 255),
(byte)Math.Min(tile.Color.B + (color.B * factor), 255));
}
This lowered time usage from 4% to 2.5%
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我的第一个问题是,为什么是浮点数?如果您只是缩放颜色以使它们褪色,则不需要太多的精度。示例:
换句话说,将您的因子表示为 0 到 256 之间的整数,并对整数进行所有计算。您不需要比 8 位更高的精度,因为结果只有 8 位。
我的第二个问题是,你是说这段代码中你从 4% 变成了 2.5% 吗?
那是很小。
使用仅进行检测或对程序计数器进行采样的分析器的人们通常会对这样的小改进感到满意。
我敢打赌,你还有其他需要花费更多时间的事情正在发生,你可以攻击它们。 以下是我的意思的示例。
My first question is, why floating point? If you're just scaling colors to fade them, you don't need a lot of precision. Example:
In other words, represent your factor as an integer from 0 to 256, and do all the calculations on integers. You don't need more precision than 8 bits because the result is only 8 bits.
My second question is, did you say you went from 4% to 2.5% in this code?
That's tiny.
People who use profilers that only do instrumentation or sample the program counter are often satisfied with such small improvements.
I bet you have other things going on that take a lot more time, that you could attack. Here's an example of what I mean.
明显的改进是在
mul
的计算中包含除法运算 (/ 255),以将除法从 3 减少到单个除法:话虽这么说,因为您要替换tile.Color ,实际上可能会更快地替换它而不是覆盖它(尽管我会对此进行分析以查看是否有帮助):
这可以防止重新计算 Alpha 通道,并且可能会稍微减少指令量。
The obvious improvement would be to include the division operation (/ 255) in the calculation of
mul
, to reduce the divisions from 3 to a single division:That being said, since you're replacing tile.Color, it may actually be faster to replace it in place instead of overwriting it (though I'd profile this to see if it helps):
This prevents the recalculation of the alpha channel, and may reduce the amount of instructions a bit.