布尔值FALSE和TRUE是否可以被重新定义?

11
我正在阅读一本关于 PHP 的书,其中涉及到使用 TRUEFALSE,它说:

事实上,小写版本更加稳定,因为 PHP 不允许您重新定义它们;而大写的可以被重新定义。

我尝试重新定义 TRUEFALSE,但不起作用!我在谷歌上搜索了有关重定义常量的信息,并发现需要使用 runkit_constant_redefine(),但我没有安装 runkit 扩展,所以无法在 TRUE 和 FALSE 上尝试。
我的问题是,TRUEtrueFALSEfalse 能否被重新定义,是否需要使用 runkit_constant_redefine()

1
你到底为什么要改变布尔值呢?难道你不能定义自己的常量吗?比如 myTruemyFalse - Sverri M. Olsen
我非常怀疑TRUE是不是与trueTrue或者tRue有所不同。这是PHP - 大小写无关紧要...有时候。外面很冷,用那本书点火吧。 - Markus Malkusch
@SverriM.Olsen 就像我说的“我正在读一本书”,所以我只是在学习和思考:D 我并不打算重新定义它们。 - user2640130
4
好的。如果我在一个项目中工作,然后有人更改了布尔值,我可能会致力于恢复死刑... ;) (注:该句话是一种幽默说法,表达作者对布尔值被更改的严重态度,并不真正意味着要推动恢复死刑。) - Sverri M. Olsen
@SverriM.Olsen https://github.com/kitcambridge/evil.js/blob/gh-pages/evil.js - ceejayoz
看这段代码片段:https://3v4l.org/S2AFZ。似乎在PHP 7中无法完成了。 - nawfal
4个回答

6

布尔值 true 被定义为不区分大小写的常量,其中 true 是默认符号。

 define("true", 1, 1);

这意味着它也可以在其他任何大小写下工作,例如 TRUETrueTrUetRUE

你的书所暗示的是再次重新定义常量为另一种大小写变量。这是可以做到的。除了小写的 true,其他大小写都是常量查找表中的空白点。

例如,使用define("True", 2)将优先于小写的true,后者将替换其他情况下的常量。

不管怎样,你的书提供的建议毫无意义。即使您可以为布尔常量声明十几个变量,但实际上没有人会这样做。所谓的“更稳定”的推理实际上是虚假的。应该选择更易读或与现有编码风格相匹配的符号。


1
我的php-5.6.0没有重新定义True。哪个php重新定义了?您还可以提供关于“true”是默认符号的参考资料吗? - Markus Malkusch
适用于所有变体的CLI运行时(已测试4.4.7、5.0、5.1)。但在PHP 5.2周围存在语义不一致。从PHP 5.3开始,您需要声明一个“命名空间”来观察它(适用于5.4、5.5、5.6)。请参见https://github.com/php/php-src/blob/master/Zend/zend_constants.c,注意大写的`REGISTER_MAIN_BOOL_CONSTANT(“TRUE”,`,但实际上还是将其小写化为`zend_register_constant`中的CONST_CS。 - mario
我明白了,这是一个实现细节。重新定义 True 显然是一个预命名空间特性。在命名空间内定义 True 是另一回事,因为你正在定义 mynamespace\True,它与 \True 不同。 - Markus Malkusch

1
你可以在每个命名空间中定义不同的truefalse
namespace foo;

define('foo\true', 0);
if (true) {
    echo 'This will be never printed.';
}

这确实会被打印出来,至少在PHP 8中是这样的。 - TwoD

0

可以,对于大写版本:

$ php
php > var_dump(defined('TRUE'), TRUE);
bool(true)
bool(true)
php > define('TRUE', 'arglebargle');
php > var_dump(defined('TRUE'), TRUE);
bool(true)
string(11) "arglebargle"

php > echo phpversion();
5.4.16

小写,不要太多:

php > var_dump(defined('true'), true);
bool(true)
bool(true)
php > define('true', 'foobarbaz');
PHP Notice:  Constant true already defined in php shell code on line 1

但是你为什么想要这样做呢?重新定义现实很少能有好结果。


3
这里的输出不同:http://codepad.viper-7.com/vPe1r2(测试了所有可用的PHP版本,不仅限于5.6.0) - Niko

-1
这是 PHP 手册 布尔值 的一部分:

the constants TRUE or FALSE. Both are case-insensitive.

$foo = True; // assign the value TRUE to $foo

if ($show_separators == TRUE) {

由于这是手册的措辞,您可以假设新版本不太可能破坏向后兼容性。您可以考虑在任何情况下都将True编写为稳定的。尽管建议使用一致的代码风格,但这与稳定性无关。

不区分大小写的常量存储为规范化的小写true是实现细节,没有进一步的相关性。


关于那些声称重新定义TRUE的人:我唯一成功的情况是在自己的命名空间中。
namespace foo;

define("TRUE", "bar");
assert (TRUE === "bar");
assert (TRUE !== \TRUE)

这里定义的是foo\TRUE,而不是\TRUE

Mario在PHP命名空间之前的版本(PHP<5.3)中编写了重新定义TRUE的代码。嗯,PHP-5.3已经发布了5年了。令人惊讶的是,PHP<5.3的市场份额约为PHP-5的23%。因此,我认为这个话题仍然具有有效的相关性。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接