在一根奇怪的绳子上排列
Permutation on a strange string
有一个由10个字符组成的奇怪字符串,分别为"0"或"1"。我有n个筛选器字符串,每个字符串包含10个字符,分别为"0"或"1"。过滤器字符串中第i个位置的"1"意味着,如果我将此过滤器应用于奇怪字符串的第i个字符,奇怪字符串的第一个字符将反转:如果它是"0",它将变为"1",反之亦然,而过滤器字符串中的第i位置的"0"对奇怪字符串没有任何作用。我可以应用任意数量的过滤器。我可以选择任意数量的过滤器,并可以应用于奇怪的字符串。现在我想知道我可以应用所有过滤器的多少不同子集来转换这个奇怪的字符串,这样奇怪的字符串只包含1?我不能将这个问题推广到任何数量的字符串。有人能帮忙吗。
让我们有一些测试用例
输入奇怪的字符串:
11111111111
过滤器字符串总数:
2
输入筛选字符串:
0000000000
0000000000
输出为:4
解释:奇怪的字符串已经有了所有字符1,我有两个不同的身份过滤器。我可以应用过滤器的空子集,只应用第一个过滤器,只应用第二个过滤器,或者两者都应用。
输入奇怪的字符串:
0101010101
过滤器字符串总数:
3
输入筛选字符串:
1010101010
1010000000
0000101010
输出为:2
解释:我可以应用第一个过滤器(并反转所有0),也可以按任何顺序应用第二个和第三个过滤器。
Brute force算法:
std::uint16_t apply_filters(std::uint16_t init,
const std::vector<std::uint16_t>& filters,
const std::vector<bool>& mask)
{
auto res = init;
for (std::size_t i = 0; i != filters.size(); ++i) {
if (mask[i]) {
res ^= filters[i];
}
}
return res;
}
bool increase(std::vector<bool>& bs)
{
for (std::size_t i = 0; i != bs.size(); ++i) {
bs[i] = !bs[i];
if (bs[i] == true) {
return true;
}
}
return false; // overflow
}
std::size_t count_filters_combination(std::uint16_t init,
const std::vector<std::uint16_t>& filters)
{
std::vector<bool> bs(filters.size());
std::size_t count = 0;
const std::uint16_t expected = 0b1111111111;
do
{
if (expected == apply_filters(init, filters, bs)) {
++count;
}
} while (increase(bs));
return count;
}
实时演示
我用python编写了我的解决方案。它应该很容易理解。我把它留给你翻译成C++。
def filterCombinations(original, filters):
combinations = 1 if original == 0b1111111111 else 0
for i in xrange(len(filters)):
newvalue = original ^ filters[i]
newfilters = filters[i+1:]
combinations += filterCombinations(newvalue, newfilters)
return combinations
使用3个过滤器,第一级递归如下所示:
filterCombinations(S, [F1, F2, F3])
--> X +
filterCombinations(S^F1, [F2, F3]) +
filterCombinations(S^F2, [F3]) +
filterCombinations(S^F3, [])
其中如果S == 1111111111
则X
为1,否则0
为1。
相关文章:
- 如何遍历几个每小时一次的根(.root)文件,并将它们组合成更大的每日数据.root文件?
- 有没有一种 STL 方法可以找到字符串的所有排列,给出一个以 C++ 为单位的大小?
- 有没有一种算法可以将 LAPACK 排列更改为真正的排列?
- Av_read_pause和av_read_play挂了一根线
- 使用增强灵气解析一根细弦
- 给定一组字符和长度的排列
- 打印可以由一组n个字符组成的长度为k的所有排列
- 一分解算法以找到多个根
- 在C++中生成一组整数的排列.获取分段错误
- C 求解四分之一根(第四阶多项式)
- 我可以用另一根线冲洗我的蒸汽吗
- 使用算术记数法横向排列一串字符
- 在执行过程中睡一根线
- 在一根奇怪的绳子上排列
- ".exe has stopped working"当我尝试串起一根绳子时
- 投掷和抓住一根绳子
- 有可能弄断一根纺线吗?
- 如何比较一根绳子和一根_T("some String")?
- 为什么我不能做一根绳子
- 如何从一组中取出一根弦