bentools / cartesian-product
一个简单、内存占用低的函数,用于生成多维数组的所有组合。
1.4.1
2022-01-19 13:31 UTC
Requires
- php: >=7.4
Requires (Dev)
- dms/phpunit-arraysubset-asserts: ^0.3.1
- php-coveralls/php-coveralls: @stable
- phpunit/phpunit: ^8.0|^9.0
- squizlabs/php_codesniffer: @stable
- symfony/var-dumper: ^3.2|^4.0
README
笛卡尔积
一个简单、内存占用低的函数,用于生成多维数组的所有组合。
用法
require_once __DIR__ . '/vendor/autoload.php'; use function BenTools\CartesianProduct\cartesian_product; $data = [ 'hair' => [ 'blond', 'black' ], 'eyes' => [ 'blue', 'green', function (array $combination) { // You can use closures to dynamically generate possibilities if ('black' === $combination['hair']) { // Then you have access to the current combination being built return 'brown'; } return 'grey'; } ] ]; foreach (cartesian_product($data) as $combination) { printf('Hair: %s - Eyes: %s' . PHP_EOL, $combination['hair'], $combination['eyes']); }
输出
Hair: blond - Eyes: blue
Hair: blond - Eyes: green
Hair: blond - Eyes: grey
Hair: black - Eyes: blue
Hair: black - Eyes: green
Hair: black - Eyes: brown
数组输出
您可以使用 foreach
将所有可能性输出到数组中。
print_r(cartesian_product($data)->asArray());
输出
Array ( [0] => Array ( [hair] => blond [eyes] => blue ) [1] => Array ( [hair] => blond [eyes] => green ) [2] => Array ( [hair] => blond [eyes] => grey ) [3] => Array ( [hair] => black [eyes] => blue ) [4] => Array ( [hair] => black [eyes] => green ) [5] => Array ( [hair] => black [eyes] => brown ) )
组合计数
您可以简单地计算数据产生的组合数量
require_once __DIR__ . '/vendor/autoload.php'; use function BenTools\CartesianProduct\cartesian_product; $data = [ 'hair' => [ 'blond', 'red', ], 'eyes' => [ 'blue', 'green', 'brown', ], 'gender' => [ 'male', 'female', ] ]; var_dump(count(cartesian_product($data))); // 2 * 3 * 2 = 12
安装
需要 PHP 7.4+。
composer require bentools/cartesian-product
性能测试
以下示例在我的 Core i7 个人电脑上执行,拥有 8GB 内存。
require_once __DIR__ . '/vendor/autoload.php'; use function BenTools\CartesianProduct\cartesian_product; $data = array_fill(0, 10, array_fill(0, 5, 'foo')); $start = microtime(true); foreach (cartesian_product($data) as $c => $combination) { continue; } $end = microtime(true); printf( 'Generated %d combinations in %ss - Memory usage: %sMB / Peak usage: %sMB', ++$c, round($end - $start, 3), round(memory_get_usage() / 1024 / 1024), round(memory_get_peak_usage() / 1024 / 1024) );
输出
在 1.61 秒内生成了 9,765,625 个组合 - 内存使用:0MB / 峰值使用:1MB
单元测试
./vendor/bin/phpunit
其他实现
patchranger/cartesian-iterator
另请参阅
致谢
Titus on StackOverflow - 你真的很棒。