最近我与我的老板(很长一段时间的C开发人员)进行了讨论,他们不鼓励我使用C ++流并坚持使用“好老”printf
&朋友。现在我可以理解他为什么这么说并且相信我,我没有听从他的建议。
但是这仍然让我感到烦恼 - 在某些情况下,C中的某些东西仍然比同样/类似的东西的C ++实现更好吗?更好的意思是例如性能,稳定性甚至代码可读性/可维护性。如果是这样,有人可以给我一些例子吗?我主要讨论像printf / streams这样的类似差异,而不是关于继承或OOP等功能。我问这一切的原因是我认为自己是 C ++ 开发人员,因此我总是尝试编写 C ++方式。
答案 0 :(得分:9)
C printf() - 样式输出通常比C ++ ostream输出更快。但当然它无法处理C ++输出的所有类型。这是我所知道的唯一优势 - 通常,由于积极的内联,C ++可以比C快很多。
答案 1 :(得分:9)
C程序员有时会指出一件事,值得考虑:如果你远离宏,那么C代码行的作用就显而易见了。以此为例:
x = y;
在C中,这是一项任务,只是一项任务。 y的值是(在可能的转换之后)复制到x。
在C ++中,这可能意味着任何。
为了使它更有趣,每个单独的操作都可能在C ++中抛出一个异常,这意味着每一行都必须以能够回滚它改变的方式编写,当你不能说什么时,这有时很难实际上是一条线。更糟糕的是,您的程序可能会立即崩溃,因为异常发生是因为在异常展开期间调用了赋值。在C ++中,事物往往变得“垂直复杂”,这对开发人员的能力和沟通技巧提出了自己的要求。
答案 2 :(得分:4)
当你编写C ++时,编写C ++。当你写C时,写一下C.无论谁说不同,可能会对这些差异感到不舒服,或者认为C ++是一个“更好的C”。情况并非如此; C ++是它自己的语言,有自己的特性,并且主要是C兼容的,只是为了简化转换。
答案 3 :(得分:4)
就性能而言,我曾经是USACO的竞争对手。我很快发现98%的程序运行时使用了C ++ IOStreams。更改为fscanf可将开销减少十倍。在性能方面,根本没有竞争。
答案 4 :(得分:3)
我认为当你需要原始内存管理时,C风格会更好。使用C ++结构执行此操作有点麻烦,例如,您没有realloc()。
有人拒绝投票,可能从未试图探讨这个话题。
我很惊讶人们无法想象自己处于不同的位置。我并不是说每个人都应该使用C风格的结构。我说当你需要原始内存管理时,C风格会更好。有人必须编写所有这些安全类/库(包括标准库,垃圾收集器,内存池)。您从未需要它的经验并不涵盖所有情况。
另一种情况是你写一个库。使用C,您可以获得漂亮的符号表,可以轻松地与许多其他编程语言绑定。使用C ++,您将拥有name mangling,这使得在非C ++环境中使用库变得更难(但并非不可能)。
答案 5 :(得分:1)
答案 6 :(得分:1)
我无法给你一个确凿的答案;然而,我发现这个相当过时的比较很有趣。
答案 7 :(得分:1)
我不认为在iostreams上使用printf样式函数是合理的。
iostream只是大大加快了开发时间和调试时间,并且更不容易出错(例如,考虑缓冲区溢出,错误的%类型说明符,错误的参数数量......最大的问题是编译器无法帮助你) 。
如果您在不需要时使用endl
,cout
不会比printf慢得多。
所以一般来说你应该使用C ++ iostreams,并且只有当分析显示关键部分因为iostream调用而花费太多时间时才会使用C风格函数优化这些部分,但请确保使用更安全的函数版本snprintf而不是sprintf。
示例:
考虑您有一个int foo
变量,您在printf
的许多地方,后来在开发过程中,您意识到您需要foo
成为double
。现在,您必须更改使用printf
的每个foo
样式调用中的类型说明符。如果你错过了一条线,欢迎来到未定义的行为。
最近我有一个案例,我的程序崩溃,因为我错过了一个简单的逗号,并且由于伟大的printf样式命令,我的编译器没有帮助我:printf("i will crash %s" /*,*/ "here");
。这不会发生在iostreams上。
当然,你不能像使用iostreams一样扩展printf和朋友的行为来使用你自己的类。
答案 8 :(得分:1)
使用C ++功能可能会有问题:
但是,如果小心使用,某些/大多数C ++功能非常方便且有用。 请记住这句话:“使用C ++,在膝盖上拍摄自己更难,但如果你这样做,那么整条腿都会花费你的费用。”
答案 9 :(得分:0)
当我不需要通用代码时,我有时更喜欢指针和memcpy
而不是迭代器和std::copy
。
对于iostream来说,它们既方便又可扩展,但在[f | s] printf / scanf很简单的情况下有很多情况。