我正在尝试开发一个算法来创建symfony模板服务。
我想检查一个模板是否存在于一个子集的路径中。
给定一个这样的参数数组(已按我所需的顺序排列):

$params = ['O', 'U', 'W', 'P']

如何输出此数组?
$urls = [
    'O/U/W/P/template',
    'O/U/W/template',
    'O/U/P/template',
    'O/U/template',
    'O/W/P/template',
    'O/W/template',
    'O/P/template',
    'O/template',
    'U/W/P/template',
    'U/W/template',
    'U/P/template',
    'U/template',
    'W/P/template',
    'W/template',
    'P/template',
    'template'
];

我可以用这样的代码执行一个参数列表(我想每个人都可以这样做):
private function getPaths($template, $params)
{
    $urls           = [];
    $alreadyPerform = [];
    $paramsCounter = count($params);

    for ($i = 0; $i < $paramsCounter; $i++) {
        for ($j = 0; $j < $paramsCounter; $j++) {
            if ($i !== $j && !in_array($params[$j], $alreadyPerform, true)) {
                $urls[] = sprintf(
                    '/%s/%s/%s.html.twig', $params[$i], $params[$j], $template
                );
            }
        }
        $alreadyPerform[] = $params[$i];
        $urls[] = sprintf('/%s/%s.html.twig', $params[$i], $template);
    }
    $urls[] = sprintf('%s.html.twig', $template);

    return $urls;
}

这个函数的工作方式和我今天想要的一样(最多3个参数),但是我想今天添加一个参数,也许以后会添加更多。
非常感谢你的帮助!
干杯。

最佳答案

使用递归,可以执行以下操作:

/**
 * @param array $elements
 * @param array $extra
 *
 * @return Generator
 */
function gen(array $elements, array $extra = []): \Generator {

    foreach ($elements as $i => $head) {
        foreach (gen(array_slice($elements, $i + 1), $extra) as $tail) {
            yield array_merge([$head], $tail);
        }
    }

    yield $extra;
}

演示:https://3v4l.org/gJB8q
或者没有递归:
/**
 * @param array $elements
 *
 * @return Generator
 */
function gen2(array $elements): \Generator {

    for ($num = count($elements), $i = pow(2, $num) - 1; $i >= 1; $i -= 2) {
        $r = [];
        for ($j = 0; $j < $num; $j += 1) {
            if ($i & (1 << ($num - $j - 1))) {
                $r[] = $elements[$j];
            }
        }

        yield $r;
    }
}

演示:https://3v4l.org/grKXo

09-27 11:24