php开发人员如何选择默认常量值?

mac*_*ict 2 php constants

通过使用php中的get_defined_constants函数,我可以看到系统和我自己定义的所有常量.

例:

<?php

define("MY_CONSTANT", 1);
print_r(get_defined_constants(true));

?>
Run Code Online (Sandbox Code Playgroud)

输出:

Array
(
    [Core] => Array
        (
            [E_ERROR] => 1
            [E_RECOVERABLE_ERROR] => 4096
            [E_WARNING] => 2
            [E_PARSE] => 4
            [E_NOTICE] => 8
            [E_STRICT] => 2048
            [E_DEPRECATED] => 8192
            [E_CORE_ERROR] => 16
            [E_CORE_WARNING] => 32
            [E_COMPILE_ERROR] => 64
            [E_COMPILE_WARNING] => 128
            [E_USER_ERROR] => 256
            [E_USER_WARNING] => 512
            [E_USER_NOTICE] => 1024
            [E_USER_DEPRECATED] => 16384
            [E_ALL] => 30719
            [DEBUG_BACKTRACE_PROVIDE_OBJECT] => 1
            [DEBUG_BACKTRACE_IGNORE_ARGS] => 2
....
Run Code Online (Sandbox Code Playgroud)

问题:他们是如何为某些常量提出整数值的?例如E_ALL,值为30719.为什么30719而不是随机数?

h2o*_*ooo 8

这一切都归结为二进制:

[E_ERROR] => 1                 //000000000000001
[E_WARNING] => 2               //000000000000010
[E_PARSE] => 4                 //000000000000100
[E_NOTICE] => 8                //000000000001000
[E_CORE_ERROR] => 16           //000000000010000
[E_CORE_WARNING] => 32         //000000000100000
[E_COMPILE_ERROR] => 64        //000000001000000
[E_COMPILE_WARNING] => 128     //000000010000000
[E_USER_ERROR] => 256          //000000100000000
[E_USER_WARNING] => 512        //000001000000000
[E_USER_NOTICE] => 1024        //000010000000000
[E_STRICT] => 2048             //000100000000000
[E_RECOVERABLE_ERROR] => 4096  //001000000000000
[E_DEPRECATED] => 8192         //010000000000000
[E_USER_DEPRECATED] => 16384   //100000000000000
[E_ALL] => 30719               //111011111111111 (everything but E_STRICT)
Run Code Online (Sandbox Code Playgroud)

如果你想要E_ERROR和E_USER_ERROR,你将执行一个按位OR语句:

define("E_ERROR_ALL", E_ERROR | E_USER_ERROR);
Run Code Online (Sandbox Code Playgroud)

这与以下相同

000000000000001 //E_ERROR
000000100000000 //E_USER_ERROR
------|-------| 
000000100000001 //Our custom E_ERROR_ALL
Run Code Online (Sandbox Code Playgroud)

因为OR它非常简单:

0 - 0 = 0
0 - 1 = 1
1 - 0 = 1
1 - 1 = 1
Run Code Online (Sandbox Code Playgroud)

检查时,我们可以简单地使用按位AND运算,如果结果大于0,则包含该位:

<?php
    $errorCode = E_PARSE | E_CORE_ERROR;

    if (($errorCode & E_PARSE) > 0) {
        echo "Error code includes E_PARSE" . PHP_EOL;
    }

    if (($errorCode & E_NOTICE) > 0) {
        echo "Error code includes E_NOTICE" . PHP_EOL;
    }

    if (($errorCode & E_CORE_ERROR) > 0) {
        echo "Error code includes E_CORE_ERROR" . PHP_EOL;
    }
?>
Run Code Online (Sandbox Code Playgroud)

会输出

Error code includes E_PARSE
Error code includes E_CORE_ERROR
Run Code Online (Sandbox Code Playgroud)

DEMO

这是有效的原因是因为AND使用以下逻辑:

0 - 0 = 0
0 - 1 = 0
1 - 0 = 0
1 - 1 = 1
Run Code Online (Sandbox Code Playgroud)

因此,如果我们10100针对E_CORE_ERROR(10000)检查自定义错误代码(),我们将得到以下操作:

    10100
AND 10000
    |----
    10000 = 16 (therefore larger than 0)
Run Code Online (Sandbox Code Playgroud)

但如果我们用E_NOTICE(01000)检查,则执行以下操作:

    10100
AND 01000
    -----
    00000 = 0 (No match)
Run Code Online (Sandbox Code Playgroud)