据我了解,所有脚本语言和核心科学程序通常都是用C编写的;这使实现变得凌乱而又直截了当。
我知道这些人想最大限度地发挥他们的性能,但是使用C字符串和C结构与使用C ++类之间确实存在区别。C ++似乎以相同的方式工作,除了虚函数外,它还存储一个类函数一次,并且该类的每个实例都调用该函数。
是什么使C更快,并且在必须是最快的项目(例如python或sqlite)中有显着区别吗?
据我了解,所有脚本语言和核心科学程序通常都是用C编写的;这使实现变得凌乱而又直截了当。
我知道这些人想最大限度地发挥他们的性能,但是使用C字符串和C结构与使用C ++类之间确实存在区别。C ++似乎以相同的方式工作,除了虚函数外,它还存储一个类函数一次,并且该类的每个实例都调用该函数。
是什么使C更快,并且在必须是最快的项目(例如python或sqlite)中有显着区别吗?
Answers:
C ++通常用于科学程序。C在该领域的流行可能正在减弱。Fortran仍然是一种流行的“低级”语言。
在C ++中,“您只为使用的东西付费”。因此,没有什么比这慢的了。特别是对于科学程序,表达式模板使使用模板引擎执行某些自定义优化来处理程序语义成为可能。
之所以选择C之类的项目是因为诸如Python之类的项目,是因为很多人(相对)完全理解C,因此大型代码库不会混淆大量贡献者中的许多人。
SQLite要求可执行代码小,而C确实有一点优势。明智地使用C ++仍然可以在嵌入式应用程序中使用,但是由于担心有害的语言功能会逐渐普及,因此C ++的使用率较低。
extern "C"
。Swig碰巧将C用作通用语言,但是您可以在C ++的C兼容子集中实现该包装,而无需调用C编译器。
我认为,原因与性能无关,而与互操作性无关。C ++语言比C语言更复杂,但是从性能的角度来看,这两种方式都没有明显的区别。一些C ++构造比C等效构造要快(比std::sort
快qsort
),并且可能有很好的示例来说明这种情况。
编辑:在互操作性方面...
基本上,C ++标准并未定义使用不同编译器/版本创建的二进制文件之间轻松实现互操作性所需的某些内容。这里最值得注意的问题是二进制文件中符号的命名约定。在C语言中,该语言定义了从代码中的每个符号到二进制符号名称的单个映射。被调用的函数my_function
将在被调用的二进制文件中创建一个符号(在二进制文件中my_function
。另一方面,由于函数重载等功能,C ++函数的名称必须为错位(在二进制文件中转换为不同的函数符号,对参数的类型和返回类型进行编码),并且该标准未定义操作的方式。反过来,这意味着可以根据编译器将C ++中的同一函数编译为不同的符号(除非extern "C"
用于强制C ++中的这些函数实现C互操作性)。
归根结底,脚本语言和本机代码之间的接口无论如何都必须是C接口,即使内部如何实现的细节可能是C / C ++ /任何其他本机语言。
(我故意不想激起语言优势的战争,C ++确实很强大,但是它也比C语言复杂得多,因为它比C语言复杂得多,有些看起来简单的事情可能会对它产生影响。性能)
std::sort
就是这样一个例子:在std::less
默认情况下使用仿函数并不比同等的C函数效率不高,但我知道所有的编译器将内联它(作为一个模板,它可用于内联),并删除所有的函数调用到的compare
仿函数。
语言并不是天生就快或慢,解释器和编译器可能会或多或少地提高效率。
除此之外,高级语言还提供通常具有运行时成本的抽象层。如果您不使用它们,则编译器可能会足够聪明,可以将它们剔除,但如果该语言的语义不允许安全地执行此操作,则可能无法实现……如果您需要它们,请自己实现使用较低级别的语言可能会比使用“慢速”语言慢。
restrict
恰当的例子:使用C或luajit的关键字-仅仅因为Mike是一个聪明的人,而且因为Lua的语义非常干净(与JavaScript相比),后者不会使其他所有vm的动态语言失去活力。