将带有数字键的数组作为对象进行转换 [英] Casting an Array with Numeric Keys as an Object

查看:25
本文介绍了将带有数字键的数组作为对象进行转换的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在研究 PHP 的转换机制,并在将数组转换为对象时遇到了一个奇怪的情况

I was poking around PHPs casting mechanism, and ran into an odd case when casting an array as an object

$o = (object) array('1'=>'/foo/bar');   
$o = new stdClass();
var_dump($o);

据我所知,PHP 属性需要使用与 PHP 变量相同的规则进行声明.即 一个有效的变量名以字母或下划线开头,后跟任何字母、数字或下划线的数量.但是,上面的代码产生以下输出

As I understand it, PHP properties need to be declared with the same rules as PHP variables. That is A valid variable name starts with a letter or underscore, followed by any number of letters, numbers, or underscores. However, the above code produces the following output

object(stdClass)#1 (1) {
  [1]=>
  string(8) "/foo/bar"
}

真正奇怪的是当您尝试访问对象中的信息时.

Where it gets really weird is when you try to access that information in the object.

var_dump($o->1);        // parse error
var_dump($o->{'1'});        // NULL 
var_dump(get_object_vars($o));  //array(0) { }

无论如何要获取 var_dump 报告在对象中的信息,或者它是否只是在请求生命周期的其余部分被锁定?(实际使用是零,我只是好奇)

Is there anyway to get at the the information that var_dump reports is in the object, or is it just locked up for the rest of the request life cycle? (practical use of this is nil, I'm just curious)

推荐答案

是的,除非转换回数组,否则它们只是被锁定了.PHP 中有一些小问题",例如在旧版本中,您可以将常量定义为数组,但永远不会访问其元素.即使现在您也可以将常量定义为资源(​​例如,define('MYSQL',mysql_connect());),尽管这会导致相当不可预测的行为,并且再次应避免.

Yes, they are just locked away unless cast back to an array. There are a few little "Gotchas" in PHP, for example in older versions you could define a constant as an array, but then never access its elements. Even now you can define a constant as a resource (e.g., define('MYSQL',mysql_connect());) although this leads to rather unpredictable behavoir and, again, should be avoided.

通常,最好尽可能避免数组到对象的强制转换.如果您确实需要这样做,请考虑创建 stdClass 的新实例,然后手动重命名所有变量,例如为 _0_1

Generally, it's best to avoid array-to-object casts if at all possible. If you really need to do this, consider creating a new instance of stdClass and then manually renaming all the variables, for example to _0, _1, etc.

$a = array('cat','dog','pheasant');
$o = new stdClass;
foreach ($a as $k => $v) {
    if (is_numeric($k)) {
        $k = "_{$k}";
    }
    $o->$k = $v;
}

刚刚对这个假设做了一个更快速的测试,是的,它们在对象上下文中正式不存在";数据已存储,但无法访问,因此是最终的私有成员.这是测试:

Just did one more quick test on this hypothesis, and yes, they officially "do not exist" in object context; the data is stored, but it's impossible to access, and is therefore the ultimate private member. Here is the test:

$a = array('one','two','three');
$o = (object)$a;
var_dump(property_exists($o, 1), property_exists($o, '1'));

输出是:

bool(false)
bool(false)

再次有趣的旁注,以下操作返回错误:

EDIT AGAIN: Interesting side-note, the following operation comes back false:

$a = array('one','two','three','banana' => 'lime');
$b = array('one','two','banana' => 'lime');

$y = (object)$a;
$z = (object)$b;

var_dump($y == $z);

这篇关于将带有数字键的数组作为对象进行转换的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆