方法,常量,变量和字段的外来名称-错误还是功能?

2021/01/14 02:41 · php ·  · 0评论

经过一些混乱的评论

我以为我问了一个问题。根据PHP手册,有效的类名称应与匹配[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*但是显然,这不是强制性的,也不适用于其他任何东西:

define('π', pi());
var_dump(π);

class{
    private $␀ = TRUE;
    public function ␀()
    {
        return $this->␀;
    }
}

$␀ = new ␀;
var_dump($␀ );
var_dump($␀->␀());

工作正常(即使我的IDE无法显示␀)。有学识的人可以帮我解决这个问题吗?我们可以使用任何Unicode吗?如果是这样,从什么时候开始?不是说我实际上使用任何东西,A-Za-z_但我很好奇。

澄清:我不是要使用Regex来验证类名,也不知道PHP是否内部使用了手册中建议的Regex。使我(以及链接的问题中的其他人)感到困惑的是,为什么这样的东西$☂ = 1完全可以在PHP中使用。PHP6应该是Unicode版本,但是PHP6处于中断状态。但是,如果没有Unicode支持,那为什么要这样做呢?

这个问题开始在标题中提到类名称,然后继续到一个示例,其中包括方法,常量,变量和字段的外来名称。这些实际上有不同的规则。让我们从不区分大小写的代码开始。

不区分大小写的标识符(类和函数/方法名称)

此处的一般准则是仅使用可打印的ASCII字符。原因是这些标识符已规范化为其小写版本,但是,此转换取决于语言环境。考虑以下以ISO-8859-1编码的PHP文件:

<?php
function func_á() { echo "worked"; }
func_Á();

该脚本可以工作吗?也许。这取决于返回的内容,这取决于语言环境:tolower(193)

$ LANG = zh_CN.iso88591 php a.php
工作了
$ LANG = en_US.utf8 php a.php

致命错误:在第3行的/home/glopes/a.php中调用未定义的函数func_Á()

因此,使用非ASCII字符不是一个好主意。但是,即使是ASCII字符,在某些区域设置中也可能造成麻烦。请参阅此讨论将来有可能通过做一个仅与ASCII字符一起使用的与语言环境无关的小写字母来解决此问题。

总而言之,如果我们对这些不区分大小写的标识符使用多字节编码,那么我们正在寻找麻烦。不仅仅是我们不能利用不区分大小写的优势。实际上,我们可能会遇到意想不到的冲突,因为使用语言环境规则,组成一个多字节字符的所有字节都会分别变成小写。在将语言环境小写规则应用于每个字节之后,两个不同的多字节字符有可能映射到相同的修改后的字节流表示形式。

区分大小写的标识符(变量,常量,字段)

由于这些标识符区分大小写,因此这里的问题不太严重。但是,它们只是被解释为字节流。这意味着,如果我们使用Unicode,则必须始终使用相同的字节表示形式。我们不能混合使用UTF-8和UTF-16;我们也不能使用BOM。

实际上,我们必须坚持使用UTF-8。在ASCII范围之外,UTF-8使用从0xc0到0xfd的前导字节,并且尾随字节在0x80到0xbf的范围内,这在手册允许的范围内。现在假设我们在UTF-16BE编码文件中使用字符“Ġ”。这将转换为0x01 0x20,因此第二个字节将被解释为空格。

当然,将多字节字符当作单字节字符读取是完全不支持Unicode的。PHP确实以编译开关“ --enable-zend-multibyte”的形式提供了一些多字节支持(从PHP 5.4开始,默认情况下已编译多字节支持,但已禁用;您可以zend.multibyte=On在php.ini中启用它。 )。这使您可以声明脚本的编码:

<?php
declare(encoding='ISO-8859-1');
// code here
?>

它还将处理BOM表,这些BOM表用于自动检测编码,并且不会成为输出的一部分。但是,有一些缺点:

  • 性能命中,包括内存和CPU。它以内部多字节编码方式存储脚本的表示形式,这会占用更多空间(并且似乎还将原始版本存储在内存中),并且还会花费一些CPU来转换编码。
  • 通常不编译多字节支持,因此测试较少(更多错误)。
  • 在其中编译了支持的安装与未编译支持的安装之间的可移植性问题。
  • 仅指解析阶段;无法解决不区分大小写的标识符所概述的问题。

最后,存在缺少规范化的问题-相同的字符可能用不同的Unicode代码点表示(独立于编码)。这可能会导致某些非常难以跟踪的错误。

您的字符被编码为0x80 0x90 0xe2或类似的东西,因此在不解释unicode时(与单个字节一起工作)它与您的regexp相匹配。

官方文档中

该类名可以是任何有效的标签,只要它不是PHP保留字即可。有效的类名称以字母或下划线开头,后跟任意数量的字母,数字或下划线。作为正则表达式,它将表示为:^[a-zA-Z_\x80-\xff][a-zA-Z0-9_\x80-\xff]*$

据我了解,当前的PHP版本具有一些unicode支持,但是并不一致。正如其他人所建议的那样,这将在PHP6中解决,该PHP6已被取消(未推迟)。在一天结束时,某些“奇异”字符将起作用,而另一些则不起作用;显然,正如您所建议的那样,最好坚持使用A-Za-z0-9_

同时,我听到有传言称,有关Unicode的讨论最近重新开始了,大概是从头开始的,因为PHP6中有关UTF-16的最初建议涉及大量的工作,却几乎没有回报。

旁注:据我了解,下一个主要的PHP版本将是PHP 5.4,它可能具有水平集成(特征),数组速记,内置HTTP服务器以及一些其他急需的功能。

http://www.mail-archive.com/internals@lists.php.net/msg35720.html

本文地址:http://php.askforanswer.com/fangfachangliangbianliangheziduandewailaimingcheng-cuowuhuanshigongneng.html
文章标签: ,  
版权声明:本文为原创文章,版权归 admin 所有,欢迎分享本文,转载请保留出处!

文件下载

老薛主机终身7折优惠码boke112

上一篇:
下一篇:

评论已关闭!