【发布时间】:2016-04-10 00:20:17
【问题描述】:
我最近一直在努力学习 C。来自 Java,令我惊讶的是您可以执行声明为“未定义”的某些操作。
这对我来说似乎非常不安全。我知道程序员有责任不执行未定义的操作,但为什么甚至允许它开始呢?例如,为什么编译器不能捕获超出范围的数组索引,甚至是悬空指针?你最终只是访问了你永远不应该访问的内存块,没有(明显的)充分的理由。
作为比较,Java 使 更加确定你不会做 任何事情愚蠢,像热蛋糕一样抛出异常。
允许这样做肯定是有原因的吗?这是什么?
回答:据我了解,主要原因是性能。此外,Java 确实有未定义的行为,尽管没有这样标记。
编辑:对 C 的限制性问题
【问题讨论】:
-
检查每个数组访问的边界会降低性能。
-
这个问题的答案是:因为这是C++。
-
编译器无法检测到所有未定义的行为 (it's the equivalent to the halting problem)。编译器会在可能的情况下尝试检测它并警告您,这会有所帮助,但 C 和 C++ 可以让您在需要时自取其辱。
-
从技术上讲,Java 也有一些(在 C 和 C++ 中)被描述为未定义、未指定等行为的部分。主要区别在于它们没有被记录下来。这包括 (a) 与线程有关的任何事情,(b) 垃圾收集器的行为,(c) 对象初始化、生命周期和终结的某些方面,(d) 用户界面库(Swing、AWT)的一些行为, (e) 一大堆与性能、延迟有关的事情……不胜枚举。
-
@Peter 请继续,因为你正在创造我的一天 :-) 但是,从你已经说过的开始:GC 的不确定性使得 Java 不适合需要可预测实时响应时间的关键任务软件(例如控制航天器或心肺机)。 (例如)必须以 100 次/秒的精确时间间隔完成某事。但是,这可能会延迟 [有时会延迟几秒钟],因为 GC“刚刚决定”在错误的时刻启动。
标签: c undefined-behavior