首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >在嵌入式开发中使用C而不是C++有什么理由吗?

在嵌入式开发中使用C而不是C++有什么理由吗?
EN

Stack Overflow用户
提问于 2009-05-01 18:51:59
回答 29查看 52.9K关注 0票数 88

问题

我的硬件上有两个编译器C++和C89

我正在考虑对类使用C++,但不使用多态性(以避免使用vtables)。我想使用C++的主要原因是:

  • 我更喜欢使用“内联”函数而不是宏definitions.
  • I’d,我喜欢使用名称空间,因为我的前缀弄乱了代码。
  • 我认为C++类型更安全一些,主要是因为模板和冗长的类型转换。
  • 我真的很喜欢重载函数和构造函数(用于自动类型转换)。

在为非常有限的硬件(4kb内存)进行开发时,您认为有任何理由坚持使用C89吗?

结论

谢谢你的回答,他们真的很有帮助!

我仔细考虑了这个主题,我将继续使用C语言,主要是因为:

  1. 预测C语言中的实际代码会更容易,如果你只有4kb的内存,这一点非常重要。
  2. 我的团队主要由C开发人员组成,因此不会经常使用高级C++功能。
  3. 我找到了一种在C编译器(C89)中内联函数的方法。

很难接受一个答案,因为你提供了这么多好的答案。不幸的是,我不能创建一个wiki并接受它,所以我会选择一个让我思考最多的答案。

EN

回答 29

Stack Overflow用户

回答已采纳

发布于 2009-05-02 16:58:30

在C++上使用C有两个原因:

  1. 对于很多嵌入式处理器来说,要么没有C++编译器,要么你必须额外付费。
  2. 我的经验是,相当大一部分嵌入式软件工程师几乎没有或根本没有C++的经验--要么是因为(1),要么是因为它往往不在电子工程学位上教授--所以最好坚持他们所知道的。

另外,原始问题和许多评论都提到了4KB的RAM。对于典型的嵌入式处理器,RAM的大小(大部分)与代码大小无关,因为代码存储在闪存中,并从闪存运行。

当然,代码存储空间的数量是需要牢记的,但随着新的、更大容量的处理器出现在市场上,除了对成本最敏感的项目之外,这不是过去所有项目的问题。

关于在嵌入式系统中使用C++的一个子集:现在有一个MISRA C++标准,这可能值得一看。

编辑:另请参阅this question,它引发了一场关于嵌入式系统的C与C++的争论。

票数 54
EN

Stack Overflow用户

发布于 2009-05-01 20:55:08

对于资源非常有限的目标,比如4KB的RAM,我会先用一些样本进行测试,然后再进行大量的工作,这些工作不能轻松地移植回纯ANSI C实现中。

嵌入式C++工作组确实提出了该语言的标准子集和标准库的标准子集。不幸的是,当C用户日志死掉的时候,我忘记了这一努力。看起来像是Wikipedia上有一篇文章,而且committee仍然存在。

在嵌入式环境中,您真的必须小心内存分配。要强制实施这种关注,您可能需要将全局operator new()及其朋友定义为甚至不能链接的内容,以便您知道它未被使用。另一方面,Placement new很可能是您的朋友,当它与稳定的、线程安全的和延迟保证的分配方案一起明智地使用时。

内联函数不会造成太多问题,除非它们足够大,以至于它们本来就应该是真正的函数。当然,它们所替换的宏也有同样的问题。

模板也可能不会造成问题,除非它们的实例化运行失控。对于您使用的任何模板,审核您生成的代码(链接映射可能有足够的线索),以确保只发生了您打算使用的实例化。

可能出现的另一个问题是与调试器的兼容性。对于其他可用的硬件调试器来说,对与原始源代码交互的支持非常有限,这并不罕见。如果您必须有效地在汇编中进行调试,那么有趣的C++名称混乱可能会给任务增加额外的混乱。

RTTI、动态类型转换、多重继承、重多态性和异常都会为它们的使用带来一定的运行时成本。如果使用这些特性,其中一些特性会使整个程序的成本降低,而其他特性只会增加需要它们的类的权重。了解差异,并在充分了解粗略的成本/收益分析的情况下明智地选择高级功能。

在小型嵌入式环境中,您可以直接链接到实时内核,也可以直接在硬件上运行。无论哪种方式,您都需要确保您的运行时启动代码正确处理特定于C++的启动琐事。这可能与确保使用正确的链接器选项一样简单,但由于直接控制通电重置入口点的源是很常见的,因此您可能需要对其进行审计,以确保它完成了所有操作。例如,在我工作的ColdFire平台上,开发工具附带了一个CRT0.S模块,该模块提供了C++初始化器,但将其注释掉。如果我直接使用它,我会对全局对象感到困惑,因为它们的构造函数根本就没有运行过。

此外,在嵌入式环境中,通常需要在使用硬件设备之前对其进行初始化,如果没有操作系统和引导加载程序,则执行此操作的是您的代码。您需要记住,全局对象的构造函数是在调用main()之前运行的,因此您需要修改本地CRT0.S (或其等效项),以便在调用全局构造函数之前完成硬件初始化。显然,main()的顶部已经太晚了。

票数 72
EN

Stack Overflow用户

发布于 2009-05-01 18:55:54

不是的。任何可能导致问题的C++语言特性(运行时多态性、RTTI等)在进行嵌入式开发时可以避免。有一个嵌入式C++开发人员社区(我记得在旧的C/C++用户杂志上读过嵌入式开发人员使用C++的专栏),如果选择这么糟糕,我不能想象他们会非常直言不讳。

票数 27
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/812717

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档