4

说我有以下内容:

class Thing {
   function __construct($id) {
     // some functionality to look up the record and initialize the object.

     return $this;
   }
}

现在给定一组 ID,我想以一组实例化的事物结束。类似于以下内容:

$ids = array(1, 2, 3, 4, 5);
$things = array_map(array('Thing', 'new'), $ids); // Doesn't work

当然,对于 Thing 类没有“新”方法,“__construct”也不受限制。我知道这可以通过循环 $ids 的额外步骤来完成,但是有没有一种巧妙的方法可以在每个使用 array_map 时调用“new Thing($id)”?

4

3 回答 3

8

它不能工作,因为没有静态方法Thing::new。您可以添加它,也可以只提供该函数作为array_map回调:

$ids = array(1, 2, 3, 4, 5);
$things = array_map(function($id){return new Thing($id);}, $ids);
于 2011-08-08T16:38:18.003 回答
2
$things = array();
foreach($ids as $id)
   $things[] = new Thing($id);

这是php的做事方式。这就是 php 语言的工作原理。如果您喜欢函数式编程、迭代器、推导式和其他 smartxxx 技巧,请考虑其他语言。

要从字面上回答您的问题,您将需要两个小功能

// replacement for "new"
function init($klass /* , param, param */) {
    $c = new ReflectionClass($klass);
    return $c->newInstanceArgs(
        array_slice(func_get_args(), 1));
}

// generic currying
function curry($fn /* , param, param */) {
    $_ = array_slice(func_get_args(), 1);
    return function() use($fn, $_) {
        return call_user_func_array($fn, 
            array_merge($_, func_get_args()));
    };
}

接着

class Thing
{
    function __construct($x, $y) {
        $this->x = $x;
        $this->y = $y;
    }
}

// curry one param
print_r(array_map(
    curry("init", "Thing"),
    array("x1", "x2", "x3"),
    array("y1", "y2", "y3")
));

// curry two params
print_r(array_map(
    curry("init", "Thing", "x"),
    array("y1", "y2", "y3")
));

它值得吗?我不这么认为。

于 2011-08-08T16:42:02.680 回答
0

从外观上看,您正在尝试检查是否已经启动了对象/类。

您可以尝试get_declared_classes()函数。if 将返回一个所有类都实例化的数组。

使用此数组,您可以检查系统中是否知道您的类,如果不知道,您可以即时启动它。

于 2011-08-08T16:46:30.150 回答