YaLinqo:PHP 对象的另一个 LINQ
特性
- .NET LINQ 到 PHP 最完整的移植,有许多其他方法。
- 原始 LINQ 的延迟计算、错误消息和其他行为。
- 所有方法都基于 PHPDoc 的 详细 PHPDoc 和在线参考。内容改编自来自 MSDN 的原始 LINQ 文档。
- 100%单元测试覆盖率。
- 在功能齐全的 LINQ 移植(YaLinqo,Ginq,Pinq)中性能最佳,至少比最接近的竞争对手快2倍,请参阅性能测试。
- 回调函数可以指定为闭包(如 function ($v) { return $v; }),PHP“函数指针”(字符串如 'strnatcmp' 或数组如 array($object, 'methodName')),string "lambdas" 使用各种语法('"$k = $v"', '$v ==> $v+1', '($v, $k) ==> $v + $k', '($v, $k) ==> { return $v + $k; }')。
- 键与值一样重要。大多数回调函数都接收值和键;转换可以应用于值和键;如果可能的话,在转换期间密钥永远不会丢失。
- 在整个代码中使用 SPL 接口 Iterator,IteratorAggregate 等,并且可以与 Enumerable 互换使用。
- 避免了冗余集合类,在任何地方都使用本机 PHP 数组。
- Composer 支持(Packagist 上的包)。
- 没有外部依赖。
实施方法
有些方法必须重命名,因为它们的名称是保留关键字。括号中给出了原始方法名称。
- Generation: cycle, emptyEnum (empty), from, generate, toInfinity, toNegativeInfinity, matches, returnEnum (return), range, rangeDown, rangeTo, repeat, split;
- Projection and filtering: cast, ofType, select, selectMany, where;
- Ordering: orderBy, orderByDescending, orderByDir, thenBy, thenByDescending, thenByDir;
- Joining and grouping: groupJoin, join, groupBy;
- Aggregation: aggregate, aggregateOrDefault, average, count, max, maxBy, min, minBy, sum;
- Set: all, any, append, concat, contains, distinct, except, intersect, prepend, union;
- Pagination: elementAt, elementAtOrDefault, first, firstOrDefault, firstOrFallback, last, lastOrDefault, lastOrFallback, single, singleOrDefault, singleOrFallback, indexOf, lastIndexOf, findIndex, findLastIndex, skip, skipWhile, take, takeWhile;
- Conversion: toArray, toArrayDeep, toList, toListDeep, toDictionary, toJSON, toLookup, toKeys, toValues, toObject, toString;
- Actions: call (do), each (forEach), write, writeLine.
总共有80多种方法。
示例
处理样本数据:
// Data
$products = array(
    array('name' => 'Keyboard',    'catId' => 'hw', 'quantity' =>  10, 'id' => 1),
    array('name' => 'Mouse',       'catId' => 'hw', 'quantity' =>  20, 'id' => 2),
    array('name' => 'Monitor',     'catId' => 'hw', 'quantity' =>   0, 'id' => 3),
    array('name' => 'Joystick',    'catId' => 'hw', 'quantity' =>  15, 'id' => 4),
    array('name' => 'CPU',         'catId' => 'hw', 'quantity' =>  15, 'id' => 5),
    array('name' => 'Motherboard', 'catId' => 'hw', 'quantity' =>  11, 'id' => 6),
    array('name' => 'Windows',     'catId' => 'os', 'quantity' => 666, 'id' => 7),
    array('name' => 'Linux',       'catId' => 'os', 'quantity' => 666, 'id' => 8),
    array('name' => 'Mac',         'catId' => 'os', 'quantity' => 666, 'id' => 9),
);
$categories = array(
    array('name' => 'Hardware',          'id' => 'hw'),
    array('name' => 'Operating systems', 'id' => 'os'),
);
// Put products with non-zero quantity into matching categories;
// sort categories by name;
// sort products within categories by quantity descending, then by name.
$result = from($categories)
    ->orderBy('$cat ==> $cat["name"]')
    ->groupJoin(
        from($products)
            ->where('$prod ==> $prod["quantity"] > 0')
            ->orderByDescending('$prod ==> $prod["quantity"]')
            ->thenBy('$prod ==> $prod["name"]'),
        '$cat ==> $cat["id"]', '$prod ==> $prod["catId"]',
        '($cat, $prods) ==> array(
            "name" => $cat["name"],
            "products" => $prods
        )'
    );
// Alternative shorter syntax using default variable names
$result2 = from($categories)
    ->orderBy('$v["name"]')
    ->groupJoin(
        from($products)
            ->where('$v["quantity"] > 0')
            ->orderByDescending('$v["quantity"]')
            ->thenBy('$v["name"]'),
        '$v["id"]', '$v["catId"]',
        'array(
            "name" => $v["name"],
            "products" => $e
        )'
    );
// Closure syntax, maximum support in IDEs, but verbose and hard to read
$result3 = from($categories)
    ->orderBy(function ($cat) { return $cat['name']; })
    ->groupJoin(
        from($products)
            ->where(function ($prod) { return $prod["quantity"] > 0; })
            ->orderByDescending(function ($prod) { return $prod["quantity"]; })
            ->thenBy(function ($prod) { return $prod["name"]; }),
        function ($cat) { return $cat["id"]; },
        function ($prod) { return $prod["catId"]; },
        function ($cat, $prods) {
            return array(
                "name" => $cat["name"],
                "products" => $prods
            );
        }
    );
print_r($result->toArrayDeep());
输出(压缩)
Array (
    [hw] => Array (
        [name] => Hardware
        [products] => Array (
            [0] => Array ( [name] => Mouse       [catId] => hw [quantity] =>  20 [id] => 2 )
            [1] => Array ( [name] => CPU         [catId] => hw [quantity] =>  15 [id] => 5 )
            [2] => Array ( [name] => Joystick    [catId] => hw [quantity] =>  15 [id] => 4 )
            [3] => Array ( [name] => Motherboard [catId] => hw [quantity] =>  11 [id] => 6 )
            [4] => Array ( [name] => Keyboard    [catId] => hw [quantity] =>  10 [id] => 1 )
        )
    )
    [os] => Array (
        [name] => Operating systems
        [products] => Array (
            [0] => Array ( [name] => Linux       [catId] => os [quantity] => 666 [id] => 8 )
            [1] => Array ( [name] => Mac         [catId] => os [quantity] => 666 [id] => 9 )
            [2] => Array ( [name] => Windows     [catId] => os [quantity] => 666 [id] => 7 )
        )
    )
)
要求
- Version 1 (stable): PHP 5.3 or higher.
- Version 2 (stable): PHP 5.5 or higher.
- Version 3 (pre-alpha): PHP 7.0 or higher.
使用
加入 composer.json
{
    "require": {
        "athari/yalinqo": "^2.0"
    }
}
在你的 php 文件中加入
require_once 'vendor/autoloader.php'; use \YaLinqo\Enumerable; // 'from' can be called as a static method or via a global function shortcut Enumerable::from(array(1, 2, 3)); from(array(1, 2, 3));
 该所有者的项目
                                                                (
                                                                该所有者的项目
                                                                (