为什么还用C编程?
本文翻译自Dr. Dobb's杂志主编Andrew Binstock的文章“Why Code in C Anymore?”,以下是翻译正文。
传统的那些选择C而不是C++的理由的说服力已经逐渐地被削弱。还有什么继续使用C的更好的理由么?
一个 Dr. Dobb's的老读者最近问我:为何人们还在使用C编程。这个话题最近曾在我们站点的评论中出现过。早期也曾出现在与一些行业公司的对话过程中,尤其是微 软。在C++早期,根据你的需要,你可以有许多使用C或C++的理由;但随着C++的演化,C的大量传统的杰出特性已经变得不那么优越了。考虑到 这些点一般是在比较两门编程语言时首先会被考虑到的,因此我们来一起看一下。
性能。通常我们都认为C++应用的性能要比C的慢。但在大多主流平台上,这个性能上的差距在今天已经变得非常小了。比 如,Alioth上的计算机基准测试报告显示C++(运行在32位Linux上)在运行基准测试时的性能要比C慢27%。其他一些研究结果显示这个差 距或略大或略小些。但在几乎所有例子中,C++都是仅次于C的运行第二快的编程语言。它通常要比运行在JVM和.NET平台上的语言快出很多。因 此,尽管C在基准测试上依旧保持有优势,但对于大多已经可以接受Java性能的应用(比如企业应用或面向客户端的应用)而言,这个差距显得并不是那么重要 了。
普遍性。在嵌入式编程领域,C仍然保持着首选语言的舒适地位,这缘于这样一个事实:每个硬件供货商都会提供一个C编译器。而大家普遍 也认为C++在嵌入式开发方面表现没有那么强势。不过,当今大多提供编程工具的组件供货商也提供了C++编译器。(但PIC微控制器方面继续保持 着例外)。这是一个正在逐渐缩水的好处。
可移植性。C++曾被认为是一个可移植的老大难(实际上在C89标准出台以前,C也是一个老大难)。然而,当今的编译器对C++语 言的核心实现的十分充分,以至于大多软件可以通过重新编译进行移植,不需要什么调整。如果真的需要进行调整的话,请提供像Brian Kernighan曾经说过的那样的使用语言中段的代码(译注:所谓语言中段的代码,即那些平台无关,不涉及可移植性的代码语法和元素)。库的可移植 性是一个更令人头疼的因素,不过C库也存在同样的问题。在C和C++中,编译器的标准遵守程度迥异,因此使用那些没有获得全面支持的新特性 (C99、C11以及C++11)将会是一个内在的风险。也就是说,C89可能是世界上最具可移植性的代码了。(为此,当可移植性成为最关心的事 情的时候,我们将选择它。例如,Lua团队就因此选择了C,当然也同样考虑到了性能因素)
应该说从性能、普遍性以及可移植性方面来讲,C仍然对C++保持着优势,但这种优势正在逐步缩小。在这点上,C++社区做得非常出色,他们让用户 去处理那些实质性问题并采纳。问题是:这些缩水的优势对C++的好处是种补偿吗?这些好处包括面向对象,异常处理,更好的类型管理,模板,更丰富 的标准库等等。没有了这些好处,每个用C实现的工程可能感觉起来就像尝试用一柄剪刀去修剪草坪。
那些特性无疑有助于代码编写,但却要因此付出代价 – 复杂性,这也是C有别于C++的重要之处。C是为数不多的几种规模短小、足够简洁的通用编程语言,你可以轻松掌握其全部内容。事实上我们确实可能需要 完整地了解一门语言的全部细节,并且还要充分了解其标准库,达到无需查看API手册即可使用的程度。我不相信这在其他主流语言中是可行的,C++,当然不行。
短小是语言的吸引力之一。你可以快速学习它并快速成为有效率的开发者。简洁则因另一个较少被谈及的特性而被提高:极致的语言可读性。我这里指的是 语义上而不是语法上的。在语义方面,C中做某件事情的方法是有限的。因此,当你阅读代码时,无论是谁编写的代码,你会确切地知道代码的行为。相反,C++ 做同一件事情有很多种方法 – C++开发者喜欢的一种灵活性。正是由于C在这方面的清晰,它才成为一门用于编写复杂基础设施的卓越编程语言。也正是这个原因,JRockit JVM(现在Oracle的主要JVM)的原始作者选择了C。在几年前的一段对话中,他们阐述了他们选择C而不是C++的观点:他们可以更快速获得开发 者;当深入到代码中时,他们可以比使用C++更容易地理解这些代码。
仅凭这一点,C语言仍然是系统层代码的一个极佳选择:它快速,可移植,易于阅读和理解。对于那些更加强调开发效率的应用,无疑C++将继续在原生语言中占据主导位置,并且很可能扩大其足迹。
© 2013, bigwhite. 版权所有.
Related posts:
c语言简单、非常符合当今计算机的硬件抽象,而且比汇编易编写。
能看到源代码的情况下,c是无敌的,c下面的库明显一点也不比其他任何一门语言少,而且明显更稳定更容易debug,是除了汇编一位唯一一个知道到底写了什么东西的语言。个人认为c++主要是为了解决闭源开发的情况下,追溯资源管理的责任的问题,谁申请的资源,就由谁释放。