Подтвердить что ты не робот

Алгоритм, который будет принимать числа или слова и находить все возможные комбинации

Я ищу алгоритм, который будет принимать числа или слова и находить все возможные варианты их вместе, а также дать мне определить, сколько значений нужно искать вместе.

Пример позволяет сказать, что строка или массив:

cat  
dog  
fish  

тогда результаты для значения 2 могут быть:

cat dog  
cat fish  
dog cat  
dog fish  
fish cat  
fish dog   

SO, результаты из набора из 3 пунктов - это 6 возможных вариаций из двух результатов, соответствующих | с 3 результатами, соответствующими ему:

cat dog fish  
cat fish dog  
dog cat fish  
dog fish cat  
fish cat dog  
fish dog cat  

... возможно больше параметров даже

Я нашел ссылку на Stackoverflow в этом примере, которая делает это, но она находится в javascript, мне интересно, знает ли кто-нибудь, как это сделать на PHP, возможно, что-то уже построено?

http://www.merriampark.com/comb.htm (мертвая ссылка)

4b9b3361

Ответ 1

Взгляните на http://pear.php.net/package/Math_Combinatorics

<?php
require_once 'Math/Combinatorics.php';
$words = array('cat', 'dog', 'fish');
$combinatorics = new Math_Combinatorics;
foreach($combinatorics->permutations($words, 2) as $p) {
  echo join(' ', $p), "\n"; 
}

печатает

cat dog
dog cat
cat fish
fish cat
dog fish
fish dog

Ответ 2

Если вы ищете, как это работает, так это то, как я получил его без php-библиотек, использующих двоичный файл.

function search_get_combos($query){
$list = explode(" ", $query);
$bits = count($list); //bits of binary number equal to number of words in query;
//Convert decimal number to binary with set number of bits, and split into array
$dec = 1;
$binary = str_split(str_pad(decbin($dec), $bits, '0', STR_PAD_LEFT));
while($dec < pow(2, $bits)) {
    //Each 'word' is linked to a bit of the binary number.
    //Whenever the bit is '1' its added to the current term.
    $curterm = "";
    $i = 0;
    while($i < ($bits)){
        if($binary[$i] == 1) {
            $curterm .= $list[$i]." ";
        }
        $i++;
    }
    $terms[] = $curterm;
    //Count up by 1
    $dec++;
    $binary = str_split(str_pad(decbin($dec), $bits, '0', STR_PAD_LEFT));
}
return $terms;
}

Обратите внимание, что это возвратит только уникальные комбинации, но может быть легко расширено, чтобы получить все возможные комбинации комбинаций, поэтому в вашем примере это выдает:

Array
(
    [0] => fish 
    [1] => dog 
    [2] => dog fish 
    [3] => cat 
    [4] => cat fish 
    [5] => cat dog 
    [6] => cat dog fish 
)

Изменить (Дополнительные пояснения)

Основная теория

Итак, во-первых, двоичные числа, которые вы, вероятно, знаете, это строка из 1 и 0. Длина номера - это число "бит", которое у него есть, например. число 011001 имеет 6 бит (числа 25 в случае, если вам интересно). Затем, если каждый бит номера соответствует одному из терминов, каждый раз, когда он подсчитывает, если бит равен 1, этот термин включается в выход, тогда как если он равен 0, он игнорируется. Итак, основная теория того, что происходит.

Ввод в код

PHP не имеет возможности подсчета в двоичном формате, но вы можете преобразовать десятичные числа в двоичные. Таким образом, эта функция фактически подсчитывается в десятичной форме и преобразует ее в двоичную. Но поскольку количество бит важно, так как каждому термину нужен свой собственный бит, вам нужно добавить ведущие 0, так что это то, что делает этот бит: str_pad(decbin($dec), $bits, '0', STR_PAD_LEFT)

Теперь эта функция использует цикл while, но поскольку количество раз, которое требуется для изменения цикла, в зависимости от количества терминов, необходимо выполнить немного математики. Если вы когда-либо работали с двоичным кодом, вы будете знать, что максимальное число, которое вы можете сделать, это 2 ^ n (где n - количество бит).

Я думаю, что это должно было покрыть все запутанные биты функции, сообщите мне, если я что-то пропустил.

Посмотрите, что происходит

Используйте следующий код для вывода используемой логики, это может сделать немного более понятным, видя его таким образом!

function search_get_combos_demo($query){
    $list = explode(" ", $query);
    $bits = count($list);
    $dec = 1;
    while($dec < pow(2, $bits)) {
        $binary = str_split(str_pad(decbin($dec), $bits, '0', STR_PAD_LEFT));
        $curterm = "";
        $i = 0;
        while($i < ($bits)){
            if($binary[$i] == 1) {
                $curterm[] = $list[$i]." ";
            }
            $i++;
        }
        //-----DISPLAY PROCESS-----//
        echo "Iteration: $dec <table cellpadding=\"5\" border=\"1\"><tr>";
        foreach($binary as $b){
            echo "<td>$b</td>";
        }
        echo "</tr><tr>";
        foreach($list as $l){
            echo "<td>$l</td>";
        }
        echo "</tr></table>Output: ";
        foreach($curterm as $c){
            echo $c." ";
        }
        echo "<br><br>";
        //-----END DISPLAY PROCESS-----//
        $terms[] = $curterm;
        $dec++;
    }
    return $terms;
}

Ответ 3

Вы можете попробовать этот открытый исходный код для этого. Он реализует итератор. Нажмите

Доступно в PHP, Java.

Вам нужно расширить его.