【问题标题】:Create an array regrouping all possibilities of another multidimentionnal array创建一个数组,重新组合另一个多维数组的所有可能性
【发布时间】:2019-02-23 08:16:13
【问题描述】:

我在转换数组时遇到了一些小困难,需要专业人士的帮助。

我有一个这样的数组:

$inputs = array(
    'size' => array(
        's' => 's',
        'm' => 'm',
        'l' => 'l',
    ),
    'color' => array(
        'red' => 'red',
        'blue' => 'blue',
    ),
    'option' => 'option 1',
);

根据这些值,我需要创建一个组合所有可能性的数组,就像这样:

$possibilities = array(
    0 => array('size' => 's', 'color' => 'red', 'option' => 'option 1'),
    1 => array('size' => 'm', 'color' => 'red', 'option' => 'option 1'),
    2 => array('size' => 'l', 'color' => 'red', 'option' => 'option 1'),
    3 => array('size' => 's', 'color' => 'blue', 'option' => 'option 1'),
    4 => array('size' => 'm', 'color' => 'blue', 'option' => 'option 1'),
    5 => array('size' => 'l', 'color' => 'blue', 'option' => 'option 1'),

);

我确切地说我在 laravel 上,所以我可以使用 collection methods,但即使使用这个辅助方法,我也找不到获得我想要的 $possibilities 数组的方法。

原始数组是动态的(可以有更多具有不同标签名称的选项),所以我需要能够工作的东西,无论数组大小和标签名称如何。

【问题讨论】:

  • 欢迎您,能否请您发布您已有的代码?
  • 这并不能完全解决您的问题,因为option 1 是一个字符串而不是一个数组,但是您可以轻松地基于它来运行代码:stackoverflow.com/questions/6311779/…
  • @JoelHinz 谢谢,你的例子似乎和我很接近,如果我能以此为基础我会尝试。

标签: php arrays laravel


【解决方案1】:
$output = array();
foreach($inputs['size'] as $size)
{
    foreach($inputs['colour'] as $colour)
    {
        foreach($inputs['option'] as $option)
        {
            $output[] = array('size' => $size, 'colour' => $colour, 'option' => $option);
        }
    }
}
return $output;

更新:

$collection = collect($inputs[0]);
array_shift($inputs);
$matrix = $collection->crossJoin($inputs);
$matrix->all();

更新:

$collection = collect(array_shift($inputs));
$matrix = $collection->crossJoin($inputs);
$matrix->all();

更新:

使用这个功能

function combinations($arrays, $i = 0) {
    if (!isset($arrays[$i])) {
        return array();
    }
    if ($i == count($arrays) - 1) {
        return $arrays[$i];
    }

    // get combinations from subsequent arrays
    $tmp = combinations($arrays, $i + 1);

    $result = array();

    // concat each array from tmp with each element from $arrays[$i]
    foreach ($arrays[$i] as $v) {
        foreach ($tmp as $t) {
            $result[] = is_array($t) ? 
                array_merge(array($v), $t) :
                array($v, $t);
        }
    }

    return $result;
}

【讨论】:

  • @siam 很好的输入,但标签在大小和名称上是变量。所以我不能依赖固定键。
  • 你的代码看起来很优雅,但我有一个错误,说 $input[0] 是未定义的偏移量。不确定您尝试使用输入创建的集合是什么[0]
  • 实际上,我正在收集您拥有的输入的第一个数组,并将其与您拥有的输入中的其余数组交叉加入
  • 不起作用,最新的更新给了我这个数组作为结果: Array ( [0] => Array ( [0] => m [1] => Array ( [red] => red [blue] => blue ) ) [1] => Array ( [0] => l [1] => Array ( [green] => vert [blue] => bleu ) ) )
  • 由于我认为的键而无法正常工作,请检查 laravel 中的文档以了解 crossJoin,它会尝试实现您想要的
【解决方案2】:

请试试这个,希望对你有帮助。

<?php

$inputs = array(
    'size' => array(
        's' => 's',
        'm' => 'm',
        'l' => 'l',
    ),
    'color' => array(
        'red' => 'red',
        'blue' => 'blue',
    ),
    'option' => 'option 1',
);
$combinations = [[]];
$length = count($inputs);

foreach (array_keys($inputs) as $key) {
    $tmp = [];
    foreach ($combinations as $v1) {
        if (is_array($inputs[$key])) {
            foreach ($inputs[$key] as $v2) {
                $tmp[] = array_merge($v1, [$key => $v2]);
            }
        } else {
            $tmp[] = array_merge($v1, [$key => $inputs[$key]]);
        }
    }
    $combinations = $tmp;
}
echo "<pre>";
print_r($combinations);

?>

【讨论】:

  • 哇,你的代码就像一个魅力!我仍然对 laravel 收集解决方案感兴趣,因为在正确的地方使用正确的方法可能会更优雅,但它真的很好用!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-07-09
  • 2019-05-24
  • 2012-12-16
  • 1970-01-01
  • 2020-02-29
  • 2023-04-03
相关资源
最近更新 更多