草庐IT

php - 不同的解释

coder 2024-04-14 原文

代码

$global_obj = null;
class my_class
{
       var $value;
       function my_class()
       {
               global $global_obj;
               $global_obj = &$this;
       }
}
$a = new my_class;
$a->my_value = 5;
$global_obj->my_value = 10;
echo $a->my_value;

回显 5,而不是 10。

“第一次检查时,my_class 的构造函数似乎在 $global_obj 变量中存储了对自身的引用。因此,人们会期望,当我们稍后将 $global_obj->my_value 的值更改为 10 时, $a 中相应的值也会改变。不幸的是,new 运算符不返回引用,而是返回新创建对象的副本。”

我还是不太明白,请哪位大侠解释一下,帮助我理解一下?

最佳答案

不确定为什么会这样,但是,如果您在将 $this 分配给全局变量时删除 & ,它将起作用.


为了说明这一点,以下代码部分:

$global_obj = null;
class my_class
{
   public $my_value;
   public function __construct()
   {
        global $global_obj;
        $global_obj = $this;
   }
}
$a = new my_class;
$a->my_value = 5;

$global_obj->my_value = 10;
echo $a->my_value;

给出以下输出:

10


以下是与您的代码的不同之处:

  • 我删除了 $this 之前的 & :对于 PHP 5,在处理对象时不需要这样做
  • 我将代码翻译成真正的 PHP 5:


作为旁注,您发布的代码应该给您以下警告:

Strict standards: Creating default object from empty value

注释:

  • 我正在使用 PHP 5.3.2
  • E_ALL 不包括 E_STRICT ( source )



经过更多搜索后编辑:

遍历 References Explained PHP 手册的部分,更具体地说是 What References Do页面,有一条警告说 (quoting) :

If you assign a reference to a variable declared global inside a function, the reference will be visible only inside the function.
You can avoid this by using the $GLOBALS array.

还有一个例子。


尝试使用 $GLOBALS在你的代码中,我有这部分代码:

$global_obj = null;
class my_class
{
   public $my_value;
   public function __construct()
   {
        $GLOBALS['global_obj'] = & $this;
   }
}
$a = new my_class;
$a->my_value = 5;

$global_obj->my_value = 10;
echo $a->my_value;

我得到以下输出:

10

这似乎有效 ;-)


如果我用这个替换 __construct 方法:

public function __construct()
{
    global $global_obj;
    $global_obj = & $this;
}

这行不通...


所以看起来你不应该在这里使用 global,而应该使用 $GLOBALS

手册中给出的解释是:

Think about global $var; as a shortcut to $var =& $GLOBALS['var'];.
Thus assigning another reference to $var only changes the local variable's reference.



而且,正是如此:使用全局变量通常不是一个好主意——而且,在这种特定情况下,感觉像是一个非常糟糕的主意...

(现在,如果这个问题只是为了理解为什么......好吧,我能理解你的好奇心;-))

关于php - 不同的解释,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2706426/

有关php - 不同的解释的更多相关文章

  1. ruby - 有人可以帮助解释类创建的 post_initialize 回调吗 (Sandi Metz) - 2

    我正在阅读SandiMetz的POODR,并且遇到了一个我不太了解的编码原则。这是代码:classBicycleattr_reader:size,:chain,:tire_sizedefinitialize(args={})@size=args[:size]||1@chain=args[:chain]||2@tire_size=args[:tire_size]||3post_initialize(args)endendclassMountainBike此代码将为其各自的属性输出1,2,3,4,5。我不明白的是查找方法。当一辆山地自行车被实例化时,因为它没有自己的initialize方法

  2. java - 为什么 ruby​​ modulo 与 java/other lang 不同? - 2

    我基本上来自Java背景并且努力理解Ruby中的模运算。(5%3)(-5%3)(5%-3)(-5%-3)Java中的上述操作产生,2个-22个-2但在Ruby中,相同的表达式会产生21个-1-2.Ruby在逻辑上有多擅长这个?模块操作在Ruby中是如何实现的?如果将同一个操作定义为一个web服务,两个服务如何匹配逻辑。 最佳答案 在Java中,模运算的结果与被除数的符号相同。在Ruby中,它与除数的符号相同。remainder()在Ruby中与被除数的符号相同。您可能还想引用modulooperation.

  3. ruby-on-rails - 在 RSpec 中,如何以任意顺序期望具有不同参数的多条消息? - 2

    RSpec似乎按顺序匹配方法接收的消息。我不确定如何使以下代码工作:allow(a).toreceive(:f)expect(a).toreceive(:f).with(2)a.f(1)a.f(2)a.f(3)我问的原因是a.f的一些调用是由我的代码的上层控制的,所以我不能对这些方法调用添加期望。 最佳答案 RSpecspy是测试这种情况的一种方式。要监视一个方法,用allowstub,除了方法名称之外没有任何约束,调用该方法,然后expect确切的方法调用。例如:allow(a).toreceive(:f)a.f(2)a.f(1)

  4. ruby - 解释为局部变量会覆盖方法名称吗? - 2

    如thisquestion,当在其自己的赋值中使用未定义的局部变量时,它的计算结果为nil。x=x#=>nil但是当局部变量的名称与现有的方法名称冲突时,就比较棘手了。为什么下面的最后一个示例返回nil?{}.instance_eval{a=keys}#=>[]{}.instance_eval{keys=self.keys}#=>[]{}.instance_eval{keys=keys}#=>nil 最佳答案 在Ruby中,因为可以在没有显式接收器和括号的情况下调用方法,所以在局部变量引用和无接收器无参数方法调用之间存在语法歧义:f

  5. 语法类似于 GitHub Flavored Markdown 的 Ruby markdown 解释器? - 2

    我使用Jekyll运行博客,并认为我会解决RedcarpetMarkdown解释器,因为它是developedandusedbyGitHub.好吧,我只是碰巧遇到了一个错误,去检查问题,然后foundthis.Maintainersays,"Asyouprobablyhavenoticed(harharharhar)Idon'thavetimetomaintainRedcarpetanymore.It'snotapriorityforme(IfindMarkdownthoroughlyboring)andit'snotapriorityforGitHub,becausewenolong

  6. ruby-on-rails - 如何用不同的用户运行nginx主进程 - 2

    A/ctohttp://wiki.nginx.org/CoreModule#usermaster进程曾经以root用户运行,是否可以以不同的用户运行nginxmaster进程? 最佳答案 只需以非root身份运行init脚本(即/etc/init.d/nginxstart),就可以用不同的用户运行nginxmaster进程。如果这真的是你想要做的,你将需要确保日志和pid目录(通常是/var/log/nginx&/var/run/nginx.pid)对该用户是可写的,并且您所有的listen调用都是针对大于1024的端口(因为绑定(

  7. ruby - 从 sinatra 中的 before do block 返回不同的值 - 2

    有没有办法在sinatra的beforedoblock中停止执行并返回不同的值?beforedo#codeishere#Iwouldliketo'return"Message"'#Iwouldlike"/home"tonotgetcalled.end//restofthecodeget'/home'doend 最佳答案 beforedohalt401,{'Content-Type'=>'text/plain'},'Message!'end如果你愿意,你可以只指定状态,这里有状态、标题和正文的例子

  8. ruby-on-rails - Sunspot:如何对具有不同值的多个字段进行全文查询? - 2

    我想用sunspot重现以下原始solr查询q=exact_term_text:fooORterm_textv:foo*ORalternate_text:bar*但我无法通过标准的太阳黑子界面理解这是否可能以及如何实现,因为看起来:fulltext方法似乎不接受多个文本/搜索字段参数我不知道将什么参数作为第一个参数传递给fulltext,就好像我通过了"foo"或"bar"结果不匹配如果我传递一个空参数,我得到一个q=*:*范围过滤器(例如with(:term).starting_with('foo*')(顾名思义)作为过滤器查询应用,因此不参与评分。似乎可以手动编写字符串(或者可能使

  9. ruby - 有人可以解释一下在 Ruby 中注入(inject)的真实、通俗易懂的用法吗? - 2

    我正在学习Ruby,遇到了inject。我正处于理解它的风口浪尖,但当我是那种需要真实世界的例子来学习一些东西的人时。我遇到的最常见的例子是人们使用inject来添加一个(1..10)范围的总和,我不太关心这个。这是一个任意的例子。在实际程序中我会用它做什么?我正在学习,所以我可以继续使用Rails,但我不必有一个以Web为中心的示例。我只需要一些我可以全神贯注的目标。谢谢大家。 最佳答案 inject有时可以通过它的“其他”名称reduce更好地理解。它是一个对Enumerable进行操作(迭代一次)并返回单个值的函数。它有许多有

  10. ruby - 拆分字符串并分配给不同的变量 - 2

    我从ui中得到日期范围为-approved_between"=>"2013-03-17-2013-03-18"我需要拆分此approved_start_date="2013-03-17"和approved_end_date="2013-03-18"...我希望使用它在mysql中查询,因为mysql中的日期格式是created_at:2012-07-2810:35:01.我正在做的是:approved=approved_between.split("")approved_start_date=approved[0]approved_end_date=approved[2]很确定这不是处

随机推荐