问题标签 [magic-methods]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
4 回答
6282 浏览

php - __callStatic()、call_user_func_array()、参考和 PHP 5.3.1

我一直在阅读 SO 和其他地方,但我似乎找不到任何结论性的东西。

有什么方法可以有效地通过此调用堆栈进行引用,从而产生下面示例中描述的所需功能?虽然这个例子并没有试图解决它,但它确实说明了这个问题:


为了激发潜在的解决方案,我将在此处添加摘要详细信息:

只关注call_user_func_array(),我们可以确定(至少在 PHP 5.3.1 中)您不能通过引用隐式传递参数:

通过显式传递数组元素$test作为引用,我们可以缓解这种情况:

当我们使用 引入类时__callStatic(),通过引用的显式调用时间参数似乎按照我的预期进行,但是会发出弃用警告(在我的 IDE 中):

省略引用运算符会TestClass::testFunction()导致$test按值传递给__callStatic(),当然也作为数组元素按值传递给testFunction()via call_user_func_array()。这会导致警告,因为testFunction()需要引用。

到处乱窜,一些额外的细节浮出水面。定义,如果写成通过__callStatic()引用返回 ( public static function &__callStatic()) 没有可见的效果。此外,将$arguments数组的元素重铸__callStatic()为引用,我们可以看到这call_user_func_array()在某种程度上按预期工作:

这些结果是预期的,因为$test不再通过引用传递,更改也不会传递回其范围。然而,这证实了它call_user_func_array()实际上是按预期工作的,而且问题肯定仅限于召唤魔法。

经过进一步阅读,这似乎是 PHP 处理用户函数和__call()/__callStatic()魔法中的一个“错误”。我仔细阅读了现有或相关问题的错误数据库,并找到了一个,但无法再次找到它。我正在考虑发布另一份报告,或请求重新打开现有报告。

0 投票
2 回答
2014 浏览

php - PHP ReflectionClass hasMethod 和 __call()

我正在创建一个响应魔术__call()方法的动态类。问题是,由于我是在已经存在的框架(Kohana)之上构建它,它使用 来检查类的方法是否存在ReflectionClass::hasMethod,并且它似乎没有触发__call()检查它是否存在的魔法方法。在这种情况下我能做什么?好像如果你动态添加方法(比如$this->{$name} = function(){})它仍然不能“看到”它

0 投票
3 回答
191821 浏览

python - python numpy.where() 是如何工作的?

我正在玩numpy和挖掘文档,我遇到了一些魔法。即我在说numpy.where()

他们如何在内部实现您能够将类似的东西传递x > 5给方法?我想这与它有关,__gt__但我正在寻找详细的解释。

0 投票
5 回答
3319 浏览

php - Php __get 和 __set 魔术方法 - 为什么我们需要这些?

在 Zend 快速入门指南http://framework.zend.com/manual/en/learning.quickstart.create-model.html我们可以看到:

我通常不使用任何魔术方法来创建我的 getter 和 setter。我在快速指南上看到了这个,我不明白为什么我们需要这个。

谁能帮我吗?

非常感谢

0 投票
4 回答
1215 浏览

php - __get() 示例通过 Zandstra

Matt Zandstra 在他的文章“PHP Objects Patterns and Practice”中给出了以下示例来说明 __get() 方法:

实际上,我们知道我们永远不会真正创建此类方法(getName 和 getAge)来返回此类静态值,而是 - 我们将在对象中创建名称和年龄属性并使用 $this 运算符返回这些属性。

我的问题是这个例子是否真的显示了实用性。如果没有,有人可以提供一个更好的例子来说明为什么人们会出于同样的目的使用 __get() 吗?

询问的理由

如果我们要在对象中使用姓名和年龄属性,那么无论如何都不会触发 __get() 函数,因为试图通过以下方式获取这些属性:

如果 name 属性是公共的,则会导致实际返回,或者如果它是私有的或受保护的,则会导致可见性错误。__get() 函数在这两种“真实”情况下都不会执行……我错过了什么吗?

我完全知道上面的代码有效。我不相信这是一个实际的例子。

0 投票
14 回答
132840 浏览

python - Python __call__ 特殊方法实战示例

我知道__call__当调用类的实例时会触发类中的方法。但是,我不知道什么时候可以使用这种特殊方法,因为可以简单地创建一个新方法并执行方法中完成的相同操作__call__,而不是调用实例,您可以调用方法。

如果有人给我这种特殊方法的实际用法,我将不胜感激。

0 投票
1 回答
3704 浏览

php - 如何将 is_callable 与 __call 一起使用?

我使用 PHP 5.3,它引入了闭包。因为我现在在我的应用程序(和框架)中都有可用的闭包,所以我使用 is_callable 来查看处理程序$callback的类型。

如果$callback is_callable,我足够了解并使用该函数/方法/闭包。如果它不可调用并且它是一个字符串,它可能是$this类中方法的名称。它可能存在,也可能不存在。如果我把它交给 PHP,它会“抛出”一个很好的致命错误(我喜欢那些)。

但我想使用mix-ins这意味着我需要魔法方法__call__call非常酷,因为它(可以)在实际函数调用之前包含逻辑。但是......如果__call调用的方法不存在之后会发生什么?当然,我可以抛出异常,但我们要等到之后才能知道。

现在的问题是 的有用性is_callable,因为在实现之后__call一切都会返回 true,因为一切都有一个后备(being __call)。

有没有办法兼得:动态方法和有用is_callable

我希望看到的是某种可缓存的魔术方法__is_callable,PHP 在is_callable(array($object, $method))调用时会“咨询”。

在 php.net 上,我找不到像我一样对此感到困惑的人。这不可能!用了__call就不能用is_callable了!?

我说得有道理吗?

PS。我已经调查过了method_exists,但这还不够好(即使我可以过滤掉所有闭包和全局函数),因为它会为私有和受保护方法以及公共方法返回 true。

编辑
我做了一个“更好”的 is_callable 来检查混音,但我认为它非常昂贵。

0 投票
3 回答
1681 浏览

php - 通过 __get() 引用返回 null

快速规格:

我正在使用__get()按引用技巧神奇地访问对象中任意深度的数组元素。

快速示例:

这不起作用,因为当$key未设置时,它会尝试null通过引用返回,这当然会抛出Only variable references should be returned by reference ...我尝试按如下方式修改它:

虽然仍然不起作用,我假设该设置$null基本上nullunset()它。

我能做些什么?谢谢!


只是想我会推广这个问题,因为它有点相关(PHP魔法和参考);__callStatic()、call_user_func_array()、参考和 PHP 5.3.1。我还没有找到答案......除了修改 PHP 核心。

0 投票
6 回答
4269 浏览

php - PHP魔术方法的实际应用——__get、__set和__call

我通常尽量远离 PHP 的魔法方法,因为它们似乎混淆了对象的公共接口。也就是说,它们似乎越来越多地被使用,至少在我读过的代码中,所以我不得不问:对于何时使用它们是否有任何共识?使用这三种魔术方法有什么共同的模式吗?

0 投票
2 回答
6731 浏览

php - PHPDoc 和 __callStatic

tl;博士

注释(在 PHPDoc 中)通过实现的函数的正确方法是什么__callStatic?更重要的是:有没有办法让 NetBeansPHPStorm 明白这些是静态方法?

动机

如果您想要更大的图景,这就是我提出这个问题的方式。

问题:在我当前的项目中,我们有很多真正应该是单例的类(数据库代理等)。不用说,我们至少有几百require_once$foo = new FooProxy();

解决方案:我创建了一个Loader类来解决这个问题,使用__callStatic魔法方法,所以我们可以说$foo = Loader::FooProxy();。它非常适合我们的目的,但是:

问题:这种方式显然在团队中使用的任何一个 IDE 中都没有类型提示。

解决方案:每个模块定义一个子类Loader,添加只路由到的方法__callStatic

问题:仅仅为了自动完成而添加实际解释的代码是不可接受的(这可以争论,但让我们暂时接受它)。

解决方案:我们不要添加任何真正的方法,只在 PHPDoc 中声明方法,如下所示:

问题FooProxy不是静态方法。以下都不是静态的:

使类抽象没有区别。大约一个小时的谷歌搜索没有找到任何解决方案。主要目标是让 IDE 了解这些功能;拥有正确的 PHPDoc 并不是必需的。