C#v.C ++性能 [英] C# v. C++ Performance
问题描述
我读到C#的JIT编译器生成非常高效的
机器代码。但是,我发现在进行广泛的数值计算时,C#的速度比C ++的速度低四分之一。我在下面给出代码示例。
C#和C ++都是作为发布版本编译的,默认情况下是优化的(C ++除了默认的/ b $ b优化之外还设置了/ Ob1)。我怀疑相对较差的C#
性能是由于使用了托管内存,但
为相关的类和方法添加''unsafe''使得
很少或没有区别。
我很欣赏有关如何使C#
性能接近C ++或者确认的建议
对于下面的代码示例,C#基本上比(非托管)C ++慢几倍。
C ++代码:
double total = 0.0;
for(int rep = 0; rep< 5; rep ++)
{
总计= = 1000.0;
for(long i = 0; i< 100000000; i ++)
{
总计+ = i / 999999.0;
双碟=总*总+ i;
双根=(总+碟)/
(200000.0 *(i + 1));
总计 - = root;
}
}
C#代码:
double total = 0.0;
for(int rep = 0; rep&l t; 5; rep ++)
{
总计/ = 1000.0;
for(long i = 0;我<
100000000; i ++)
{
总计+ =
i / 999999.0;
双碟=
总计*总计+ i;
双根=
(总计+光盘)/(200000.0 *(i + 1));
total - = root;
}
}
本机代码中的长32位(C / C ++)但在托管代码中是64位,更改
.... for(long i = 0; i<> 100000000; i ++)in C#code into for(int
i = ...
Willy。
" Nigel"< ni *** @ nigelwilson.evesham.net .remove_this>写在留言中
news:0a **************************** @ phx.gbl。 ..我读到C#的JIT编译器生成了非常高效的机器代码。但是,我发现在进行广泛的数值计算时C#小于第四,C ++的速度。我给出了下面的代码示例。将C#和C ++编译为默认的发布版本
优化(C ++除了默认优化之外还设置了/ Ob1)。我怀疑相对较差的C#
性能是由于使用了托管内存,但是对相关的类和方法添加不安全会使得很少或没有区别。
性能接近C ++的建议,或者对下面的代码示例的确认,C#从根本上说要慢几倍C ++代码:
对于(int rep = 0; rep< 5; rep ++)
{
总计/ = 1000.0;
for(long i = 0; i< 100000000; i ++)
{
总数+ = i / 999999.0;
双碟=总*总+ i;
双根=(总+碟)/
(200000.0 *(i + 1));
总计 - = root;
}
C#代码:
for double total = 0.0;
for(int rep = 0; rep< 5; rep ++)
{
总计/ = 1000.0;
for(long i = 0; i<
100000000; i ++)
{
总计+ =
i / 999999.0;
双碟=
总*总+ i;
双根=
(总+碟)/(200000.0 *(i + 1));
总计 - = root;
}
}
我不能提供更多的评论那一刻,但根据我的经验
数值计算恰恰是C#应该与C ++相同的区域。我已经用C#获得了非常好的结果,用于强烈的数值计算。如果,出于某种原因,你最终发现C#不会这样做(我会感到惊讶),你可以随时把最好的表现
$ b使用C或C ++中的$ b敏感代码(即使在非托管DLL中)并从C#中调用它。
我之前已经完成了非常好的结果(仅因为某些代码是
)
已经在C)中。使用PInvoke的表现非常好。
HTH
" Nigel" < NI *** @ nigelwilson.evesham.net.remove_this>在消息中写道
news:0a **************************** @ phx.gbl ... < blockquote class =post_quotes>我读到C#的JIT编译器生成非常高效的机器代码。但是,我发现在进行广泛的数值计算时,C#小于C ++速度的四分之一。我在下面给出代码示例。将C#和C ++编译为发布版本,默认优化(C ++除了默认优化之外还设置了/ Ob1)。我怀疑相对较差的C#
性能是由于使用了托管内存,但是对相关的类和方法添加不安全会使得很少或没有区别。
性能接近C ++的建议,或者对下面的代码示例的确认,C#从根本上说要慢几倍C ++代码:
对于(int rep = 0; rep< 5; rep ++)
{
总计/ = 1000.0;
for(long i = 0; i< 100000000; i ++)
{
总数+ = i / 999999.0;
双碟=总*总+ i;
双根=(总+碟)/
(200000.0 *(i + 1));
总计 - = root;
}
C#代码:
for double total = 0.0;
for(int rep = 0; rep< 5; rep ++)
{
总计/ = 1000.0;
for(long i = 0; i<
100000000; i ++)
{
总计+ =
i / 999999.0;
双碟=
总*总+ i;
双根=
(总+碟)/(200000.0 *(i + 1));
总计 - = root;
}
}
Nigel< ni *** @ nigelwilson.evesham。 net.remove_this>写道:我读到C#的JIT编译器生成非常高效的机器代码。
C#没有JIT编译器。 .NET有一个JIT编译器。你需要非常明确边界的位置。
然而,我发现在进行广泛的数值计算时C#小于a
第四个C ++的速度。我在下面给出代码示例。将C#和C ++编译为发布版本,默认优化(C ++除了默认优化之外还设置了/ Ob1)。我怀疑相对较差的C#
性能是由于使用了托管内存,但是对相关的类和方法添加不安全会使得很少或没有区别。
性能接近C ++的建议,或者对下面的代码示例的确认,C#从根本上说要慢几倍比(非托管)C ++。
C#本身是一种语言,而不是一种实现。但是,假设
实际上不是问题......从根本上说这是一个非常奇怪的词语
在这里使用 - 毫无疑问会产生某些基准测试
其中C ++最终比C#慢 - 两种语言本身怎么样? />
每个都是从根本上的比其他更慢?
在某些情况下,C ++会比C#更快,而副本
$ b $反之亦然。
现在,让我们来看看你的情况。以下是我的笔记本电脑的原始数字 - 不是理想的测试方案,但不是一个糟糕的起点:
首次运行:
C ++:27s
C#:70s
这已经不到你引用的四倍 - 实际上,
它甚至不是慢三倍。不过,让我们看看我们能做些什么...
这里看起来有很多从长到两的铸造。更改
C#代码:
for(int rep = 0; rep< 5; rep ++)
{
总计= = 1000.0;
for(double i = 0; i< 100000000d; i + = 1.0d)
{
总计+ = i / 999999.0;
双碟=总*总+ i;
双根=(总+碟)/( 200000.0 *(i + 1.0d));
总计 - = root;
}
}
C#的执行时间缩短到18秒! (结果
看起来是一样的,我不明白为什么它不是一个完美的
有效优化来执行 - 唯一可能的损失精确度
将转换(i + 1)转换为双倍会产生不同的
结果,将1.0加到i的双倍值。我已经验证
不会出现在0-100000000范围内的任何地方;在实际代码中你可能想要检查它是否有问题。
以类似的方式更改C ++代码似乎没有帮助它。
因此,根据以上所述,你会承认 ; C#是
从根本上明显快于(非托管)C ++,或者你是否会b / b
承认单个基准测试不一定是一个好的指示
整个平台?
-
Jon Skeet - < sk *** @ pobox.com>
< a rel =nofollowhref =http://www.pobox.com/~sk eettarget =_ blank> http://www.pobox.com/~skeet
如果回复小组,请不要给我发邮件
I read that C#''s JIT compiler produces very efficient
machine code. However, I''ve found when performing
extensive numerical calculations that C# is less than a
fourth the speed of C++. I give code examples below. Both
C# and C++ were compiled as release builds with default
optimisation on (C++ has /Ob1 set in addition to default
optimizations). I suspected the relatively poor C#
performance was due to using managed memory, but
adding ''unsafe'' to relevant classes and methods makes
little or no difference.
I''d appreciate advice on how I can bring the C#
performance close to that of C++, or an acknowledgement
that for the code samples below, C# is fundamentally
several times slower than (unmanaged) C++.
C++ Code:
double total = 0.0;
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (long i = 0; i < 100000000; i++)
{
total += i/999999.0;
double disc = total*total + i;
double root = (total + disc)/
(200000.0*(i + 1));
total -= root;
}
}
C# Code:
double total = 0.0;
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (long i = 0; i <
100000000; i++)
{
total +=
i/999999.0;
double disc =
total*total + i;
double root =
(total + disc)/(200000.0*(i + 1));
total -= root;
}
}
Longs 32bit in native code (C/C++) but are 64 bit in managed code, change
.... for (long i = 0; i < > 100000000; i++) in you C# code into for (int
i=...
Willy.
"Nigel" <ni***@nigelwilson.evesham.net.remove_this> wrote in message
news:0a****************************@phx.gbl...I read that C#''s JIT compiler produces very efficient
machine code. However, I''ve found when performing
extensive numerical calculations that C# is less than a
fourth the speed of C++. I give code examples below. Both
C# and C++ were compiled as release builds with default
optimisation on (C++ has /Ob1 set in addition to default
optimizations). I suspected the relatively poor C#
performance was due to using managed memory, but
adding ''unsafe'' to relevant classes and methods makes
little or no difference.
I''d appreciate advice on how I can bring the C#
performance close to that of C++, or an acknowledgement
that for the code samples below, C# is fundamentally
several times slower than (unmanaged) C++.
C++ Code:
double total = 0.0;
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (long i = 0; i < 100000000; i++)
{
total += i/999999.0;
double disc = total*total + i;
double root = (total + disc)/
(200000.0*(i + 1));
total -= root;
}
}
C# Code:
double total = 0.0;
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (long i = 0; i <
100000000; i++)
{
total +=
i/999999.0;
double disc =
total*total + i;
double root =
(total + disc)/(200000.0*(i + 1));
total -= root;
}
}
I can''t offer much more than a comment at the moment, but in my experience
numerical calculations are precisely the area where C# should be on equal
ground with C++. I''ve had very good results with C# for intense numerical
computations. If, for some reason, you end up finding out the C# won''t do
the job (I''d be surprised), you could always put the most performance
senstive code in C or C++ (even in an unmanaged DLL) and call it from C#.
I''ve done that before with very good results (only because some code was
already in C). The performance using PInvoke was really good.
HTH
"Nigel" <ni***@nigelwilson.evesham.net.remove_this> wrote in message
news:0a****************************@phx.gbl...I read that C#''s JIT compiler produces very efficient
machine code. However, I''ve found when performing
extensive numerical calculations that C# is less than a
fourth the speed of C++. I give code examples below. Both
C# and C++ were compiled as release builds with default
optimisation on (C++ has /Ob1 set in addition to default
optimizations). I suspected the relatively poor C#
performance was due to using managed memory, but
adding ''unsafe'' to relevant classes and methods makes
little or no difference.
I''d appreciate advice on how I can bring the C#
performance close to that of C++, or an acknowledgement
that for the code samples below, C# is fundamentally
several times slower than (unmanaged) C++.
C++ Code:
double total = 0.0;
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (long i = 0; i < 100000000; i++)
{
total += i/999999.0;
double disc = total*total + i;
double root = (total + disc)/
(200000.0*(i + 1));
total -= root;
}
}
C# Code:
double total = 0.0;
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (long i = 0; i <
100000000; i++)
{
total +=
i/999999.0;
double disc =
total*total + i;
double root =
(total + disc)/(200000.0*(i + 1));
total -= root;
}
}
Nigel <ni***@nigelwilson.evesham.net.remove_this> wrote:I read that C#''s JIT compiler produces very efficient
machine code.
C# doesn''t have a JIT compiler. .NET has a JIT compiler. You need to be
very clear on where the boundaries are.
However, I''ve found when performing
extensive numerical calculations that C# is less than a
fourth the speed of C++. I give code examples below. Both
C# and C++ were compiled as release builds with default
optimisation on (C++ has /Ob1 set in addition to default
optimizations). I suspected the relatively poor C#
performance was due to using managed memory, but
adding ''unsafe'' to relevant classes and methods makes
little or no difference.
I''d appreciate advice on how I can bring the C#
performance close to that of C++, or an acknowledgement
that for the code samples below, C# is fundamentally
several times slower than (unmanaged) C++.
C# itself is a language, not an implementation. However, assuming that
weren''t actually a problem... "fundamentally" is a very strange word to
use here - there are certain benchmarks that could no doubt be produced
where C++ ends up slower than C# - how can two languages themselves
each be "fundamentally" slower than the other?
There are certain situations where C++ will be faster than C#, and vice
versa.
Now, let''s look at your case in point. Here are the raw numbers from my
laptop - not the ideal testing scenario, but not a bad starting point:
First run:
C++: 27s
C#: 70s
Already this is less than the factor of four you were quoting - indeed,
it''s not even three times as slow. Still, let''s see what we can do...
There looks to be a lot of casting from long to double here. Changing
the C# code to:
for (int rep = 0; rep < 5; rep++)
{
total /= 1000.0;
for (double i = 0; i < 100000000d; i+=1.0d)
{
total += i/999999.0;
double disc = total*total + i;
double root = (total + disc)/(200000.0*(i + 1.0d));
total -= root;
}
}
the execution time for C# goes down to just 18 seconds! (The results
appear to be the same, and I can''t see why it wouldn''t be a perfectly
valid optimisation to perform - the only possible loss of precision
would be where converting (i+1) to a double would have a different
result to adding 1.0 to the double value of i. I''ve verified that
doesn''t occur anywhere in the range 0-100000000; in actual code you
might want to check whether or not it could be a problem.
Changing the C++ code in a similar way doesn''t appear to help it.
So, according to the above, would you acknowledge that "C# is
fundamentally significantly faster than (unmanaged) C++" or would you
acknowledge that single benchmarks aren''t necessarily a good indication
of an entire platform?
--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet
If replying to the group, please do not mail me too
这篇关于C#v.C ++性能的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!