使用魔术调试值(例如0xDEADBEEF)作为文字的危险究竟是什么?

Yuv*_*dam 2 language-agnostic hex programming-languages literals

毫无疑问,使用硬编码的十六进制文字指针是一种灾难:

int *i = 0xDEADBEEF;
// god knows if that location is available
Run Code Online (Sandbox Code Playgroud)

但是,使用十六进制文字作为变量的危险究竟是什么?

int i = 0xDEADBEEF;
// what can go wrong?
Run Code Online (Sandbox Code Playgroud)

如果这些值由于在各种调试场景中使用确实是"危险的" ,那么这意味着即使我不使用这些文字,任何在运行时碰巧偶然发现其中一个值的程序可能会崩溃.

有人想解释使用十六进制文字的真正危险吗?


编辑:只是为了澄清,我不是指源代码中常量的常规用法.我特别谈到可能会出现使用十六进制值的调试方案问题,具体的例子是0xDEADBEEF.

Jon*_*eet 11

使用十六进制文字不会比任何其他文字更危险.

如果您的调试会话最终在没有您想要的情况下将数据作为代码执行,那么您无论如何都处于痛苦的世界.

当然,正常的"神奇价值"与"有名的恒定"代码气味/清洁问题有关,但这并不是我认为你所谈论的那种危险.


S.L*_*ott 5

除了少数例外,没有什么是"不变的".

我们更喜欢称它们为"慢变量" - 它们的值变化太慢以至于我们不介意重新编译以改变它们.

但是,我们不希望通过应用程序或测试脚本拥有许多0x07实例,其中每个实例具有不同的含义.

我们想在每个常量上加上一个标签,使其完全明确,意味着什么.

if( x == 7 )
Run Code Online (Sandbox Code Playgroud)

"7"在上述陈述中的含义是什么?它是一样的吗?

d = y / 7;
Run Code Online (Sandbox Code Playgroud)

那是"7"的意思吗?

测试用例是一个略有不同的问题.我们不需要对数字文字的每个实例进行广泛,仔细的管理.相反,我们需要文档.

我们可以 - 在某种程度上 - 通过在代码中包含一点点提示来解释"7"的来源.

assertEquals( 7, someFunction(3,4), "Expected 7, see paragraph 7 of use case 7" );
Run Code Online (Sandbox Code Playgroud)

应该说明一个"常数" - 并命名 - 恰好一次.

单元测试中的"结果"与常数不同,需要一点小心来解释它的来源.

  • 我不是指使用命名良好的常量的问题.我在谈论使用所述常量的调试方案. (2认同)