php – 如何生成受限制的变换的排列?
作者:互联网
最好用一个例子来解释.
假设您有一个替换列表,将使用PHP,因为这是我的目标:
$s = array(
'p' => array('b', 'f', 'v'),
'a' => array('e'),
't' => array('d', '')
);
上述意味着’p’可以用’b’,’f’或’v’代替; ‘e’;’a’;并且’不’或’不’.每次只允许对每个列表进行一次替换.
所以产生’pa’的所有替换将给出:’ba’,’fa’,’va’,’pe’,’be’,’fe’,’ve’
并产生’papa’的所有替换:’baba’,’fafa’,’vava’,’pepe”bebe’,’fefe’,’veve’
我可以很容易地通过上层元素进行置换:
// 2 ^ count($s) permutations, assuming count($s) < 31
$k = 1 << count($s);
for ($l = 0; $l < $k; $l++)
{
$x = $input;
for ($m = $l, reset($s); $m; $m >>= 1, next($s))
if ($m & 1)
// Will fail here, maybe this should be an outer loop but how?
// For now, just replacing with the first element
$x = str_replace(key($s), current($s)[0], $x);
print $x."\n";
}
只是不能正确地围绕如何做正确的内部替换.
我考虑过将$s转换为一系列简单的替换:
$t = array(
array('p' => 'b'),
array('a' => 'e'),
array('p' => 'b', 'a' => 'e'),
array('p' => 'f'),
...
但这仍然让我回到了同样的问题.
任何意见,将不胜感激.
解决方法:
你对for循环的管理与数组指针的结合过于复杂.
以下是一种非常天真的方法,可以通过采用其他策略(如递归)来简化.
function generate_permutations($subtitutions, $subject) {
$permutations = array($subject);
foreach ($subtitutions as $search => $replacements) {
$new_permutations = array();
foreach ($replacements as $replacement) {
foreach ($permutations as $permutation) {
if (strpos($permutation, $search) === false) {
continue;
}
$new_permutations[] = str_replace($search, $replacement, $permutation);
}
}
$permutations = array_merge($permutations, $new_permutations);
}
return $permutations;
}
注意:我只测试了您的示例.
标签:php,algorithm,combinatorics 来源: https://codeday.me/bug/20190703/1361776.html