为什么我的C++;在Core i7上,应用程序速度比我的C应用程序(使用相同的库)快 我有一个C语言库,我有2个应用程序,用C++和C编写的。这个库是一个通信库,所以其中的一个API调用看起来是这样的: int source_send( source_t* source, const char* data ); source_t* source = source_create(); for( int i = 0; i < count; ++i ) source_send( source, "test" );

为什么我的C++;在Core i7上,应用程序速度比我的C应用程序(使用相同的库)快 我有一个C语言库,我有2个应用程序,用C++和C编写的。这个库是一个通信库,所以其中的一个API调用看起来是这样的: int source_send( source_t* source, const char* data ); source_t* source = source_create(); for( int i = 0; i < count; ++i ) source_send( source, "test" );,c++,c,hardware,cpu,cpu-architecture,C++,C,Hardware,Cpu,Cpu Architecture,在C应用程序中,代码执行如下操作: int source_send( source_t* source, const char* data ); source_t* source = source_create(); for( int i = 0; i < count; ++i ) source_send( source, "test" ); source\u t*source=source\u create(); 对于(int i=0;i未看到完整代码或程序集,我最好的猜测是

在C应用程序中,代码执行如下操作:

int source_send( source_t* source, const char* data );
source_t* source = source_create();
for( int i = 0; i < count; ++i )
    source_send( source, "test" );
source\u t*source=source\u create();
对于(int i=0;i

C++应用程序在哪里:

struct Source
{
    Source()
    {
        _source = source_create();
    }

    bool send( const std::string& data )
    {
        source_send( _source, data.c_str() );
    }

    source_t* _source;
};

int main()
{
    Source* source = new Source();
    for( int i = 0; i < count; ++i )
        source->send( "test" );
}
struct源代码
{
资料来源()
{
_source=source_create();
}
bool发送(const std::字符串和数据)
{
source_send(_source,data.c_str());
}
源_t*_源;
};
int main()
{
Source*Source=新源();
对于(int i=0;i发送(“测试”);
}
在英特尔核心I7上,C++代码每秒几乎产生50%个以上的消息。 而在Intel Core 2 Duo上,它每秒产生的消息量几乎完全相同。(core i7有4个core,每个core有2个处理线程)

我很好奇,硬件执行了什么样的魔法来实现这一点。我有一些理论,但我想我会得到一个真正的答案:)

编辑:来自评论的附加信息

编译器是VisualC++,所以这是一个窗口框(两者)


通信库的实现创建了一个新线程来发送消息。创建此线程的源是什么。

核心i7是超线程的-您是否启用了HT


也许C++代码是利用HT而编译的,而C代码却没有。运行代码时,任务管理器是什么样子的?均匀分布的负载跨越多少个内核,或者几个内核被耗尽了?

从检查源代码,我看不出为什么C++代码应该更快。 接下来我要做的是检查正在生成的汇编代码。如果您使用的是GNU工具链,那么有几种方法可以做到这一点

您可以要求gcc和g++通过
-S
命令行参数输出汇编代码。确保在添加该参数后,使用与常规编译完全相同的命令行参数

第二个选项是使用gdb加载程序,并使用
disas
命令

祝你好运

更新

您可以使用Microsoft工具链执行相同的操作

要使编译器输出程序集,可以使用以下两种方法之一。第一个应该只输出程序集,而第二个将混合程序集和源(这将使其更易于遵循)


至于使用调试器,一旦在Visual Studio中启动了调试器,请导航到“Debug | Windows | Disassembly”(在Visual Studio 2005上验证,其他版本可能会有所不同)。

只是一个猜测:如果您正在编译库源代码以及应用程序,并且C API函数未声明为extern“C”,那么C++版本可能使用了不同的、不知何故的调用约定??

也可以,如果你编译库源和你的应用程序,那么C++编译器可能是编译你的库源作为C++,并且在某种程度上比C编译器更好。

我建议做的第一件事是对两个版本进行配置,看看是否有明显的差异。 是不是C版本复制了一些不必要的东西(它可能是一个微妙的优化,或者不像返回值优化那样微妙)

这应该出现在一个好的分析器中,如果你有一个更高端的VS SKU,那么基于采样的分析器就在那里,如果你正在寻找一个好的免费分析器,那么Windows性能分析器对于Vista和更高版本来说是非常强大的

我自己可能要做的第一件事是进入调试器并检查每个调试器的反汇编,看看它们是否明显不同。注意,有一个编译器选项可以将asm输出到文本文件

如果没有明显的东西(比如额外的副本),我会用个人资料来跟进

还有一件事,如果您担心超级线程会妨碍您,请将进程硬关联到非HT内核。您可以通过GUI中的任务管理器或SetThreadAffinityMask执行此操作


瑞克

< P>未看到完整代码或程序集,我最好的猜测是C++编译器正在为您内联。C++编译器的一个优点是能够为速度快速地嵌入任何东西,而微软编译器则无端的内嵌到几乎不合理的可执行文件的膨胀点。编译器设置?运行时间?比较发出的目标代码?您是否也在编译C库?或者它已经为您编译好了?source_send()是内联定义的吗?我很难把它放到编译器上。我正在使用VisualStudio,因此它应该生成可以在所有windows计算机上运行的代码,而不考虑内核。现在,如果我使用gcc-mtune=native进行编译,我们可能会有一些东西,但这不是问题所在case@Emile:函数不是内联函数,我也编译库。除非在source_send的实现中隐藏线程,否则没有线程,并且此功能不会产生编译器代码生成问题。process explorer中有8个内核,在处理这两个应用程序时,4个窗口显示活动。如果我必须测量这个级别,我会说C++应用程序使用更多的CPU,但是一般来说它们看起来都是参与的。不幸的是,这个项目还没有准备好在Linux上编译,但是非常好的想法+1 /FA是一种整洁的,我会做比较,看看我是否能发现任何东西,我已经确保VisualStudio正在编译C代码作为C代码。使用extern“C”并在编译器上设置/TC选项