此代码当前输出
0
1
0
1
1
2
F0
0
1
0
1
1
2
F1
0
1
0
1
1
3
F0
0
1
0
1
1
3
F1
0
1
0
1
1
4
F0
等。
我正在尝试使用蛮力找出绿色,黄色,紫色,橙色,红色和蓝色的正确值
这些值不能重复(即如果red = 0则blue!= 0),但是我认为这段代码将为我提供多种解决方案,从中我可以选择正确的解决方案。
我的问题是:这有什么问题?
#include <iostream>
using namespace std;
int main()
{
int green, yellow, purple, orange, red, blue, finalresult;
int result1, result2, result3, result4, result5, result6, fresult1, fresult2;
for (green = 0; green < 10; green++)
{
for (yellow = 0; yellow < 10; yellow++)
{
for (yellow = yellow; yellow == green; yellow++)
{
yellow = yellow;
}
for (purple = 0; purple < 10; purple++)
{
for (purple = purple; purple == yellow; purple++)
{
purple = purple;
}
for (orange = 0; orange < 10; orange++)
{
for (orange = orange; orange == purple; orange++)
{
orange = orange;
}
for (red = 1; red < 10; red++)
{
for (red = red; red == purple; red++)
{
red = red;
}
for (blue = 1; blue < 10; blue++)
{
for (blue = blue; blue == red; blue++)
{
blue = blue;
}
finalresult = 0;
if(green * yellow == purple * 10 + green)
{
cout << green << endl << yellow << endl << purple << endl << orange << endl << red << endl << blue << endl;
cout << "F" << finalresult << endl;
finalresult++;
}
if (purple * 10 + orange / red == red)
{
cout << green << endl << yellow << endl << purple << endl << orange << endl << red << endl << blue << endl;
cout << "F" << finalresult << endl;
finalresult++;
}
if (yellow * 10 + orange == red * blue)
{
cout << green << endl << yellow << endl << purple << endl << orange << endl << red << endl << blue << endl;
cout << "F" << finalresult << endl;
finalresult++;
}
if (green == red * 10 + green / blue)
{
cout << green << endl << yellow << endl << purple << endl << orange << endl << red << endl << blue << endl;
cout << "F" << finalresult << endl;
finalresult++;
}
if (finalresult == 4)
{
cout << "V" << endl <<"V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl << "V" << endl;
cout << green << endl << yellow << endl << purple << endl << orange << endl << red << endl << blue << endl;
}
}
}
}
}
}
}
}
答案 0 :(得分:1)
如果我理解这个问题,则必须在所有可能的不同颜色值组合之间进行选择,以解决您的四个方程式。
OP代码中的嵌套循环将提供(几乎有一些循环从1开始)所有可能的组合,但是选择排除重复值的方式是完全错误的。
方程也可以在一个条件下检查。
以下代码应提供预期的结果:
#include <iostream>
int main(void)
{
long int n = 0, solutions = 0;
for (int green = 0; green < 10; ++green)
{
for (int yellow = 0; yellow < 10; ++yellow)
{
if ( yellow == green ) // skip the duplicate values
continue;
for (int purple = 0; purple < 10; ++purple)
{
if ( purple == green || purple == yellow )
continue;
for (int orange = 0; orange < 10; ++orange)
{
if ( orange == green || orange == yellow || orange == purple )
continue;
for (int red = 0; red < 10; ++red)
{
if ( red == green || red == yellow ||
red == purple || red == orange)
continue;
for (int blue = 0; blue < 10; ++blue)
{
if ( blue == green || blue == yellow ||
blue == purple || blue == orange || blue == red )
continue;
// Now check if the values solve all the equations
// Assuming that you don't want integer divisions
if ( purple * 10 + green == green * yellow
&& purple * 10 + orange == red * red
&& yellow * 10 + orange == red * blue
&& red * 10 + green == green * blue)
{
std::cout << "Green: " << green
<< "\nYellow: " << yellow
<< "\nPurple: " << purple
<< "\nOrange: " << orange
<< "\nRed: " << red
<< "\nBlue: " << blue << '\n';
++solutions;
}
++n;
}
}
}
}
}
}
// The number of different combinations should be 10 * 9 * 8 * 7 * 6 * 5 = 151200
std::cout << "\nCombinations tested: " << n
<< " (out of " << 10*10*10*10*10*10 << ")\n"
<< "Solutions: " << solutions << '\n';
}
执行后,将输出:
Green: 5 Yellow: 3 Purple: 1 Orange: 6 Red: 4 Blue: 9 Combinations tested: 151200 (out of 1000000) Solutions: 1
编辑
受Jarod42的answer的启发,我想展示一个更有效的解决方案,该解决方案利用了标准库函数std::next_permutation
(和std::prev_permutation
的优势) ),而不是跳过不需要的排列,而是直接生成所需的排列。
#include <iostream>
#include <vector>
#include <array>
#include <algorithm>
#include <numeric>
// Applies f() to all the permutations of n values taken k at a time
// where k is the size of the range [first, last)
// n!/(n − k)! iterations are performed
template<class Iterator, class Func>
void for_each_n_permute_k(int n, Iterator first, Iterator last, Func f);
int main()
{
std::array<int, 6> chosen;
int solutions = 0;
for_each_n_permute_k(10, chosen.begin(), chosen.end(), [&chosen, &solutions] () {
auto & [green, yellow, purple, orange, red, blue] = chosen;
if ( purple * 10 + green == green * yellow
&& purple * 10 + orange == red * red
&& yellow * 10 + orange == red * blue
&& red * 10 + green == green * blue)
{
std::cout << "Solution found (" << ++solutions << ")\n"
<< "Green: " << green
<< "\nYellow: " << yellow
<< "\nPurple: " << purple
<< "\nOrange: " << orange
<< "\nRed: " << red
<< "\nBlue: " << blue << '\n';
}
});
}
// copy the elements from [it1, last) to dest if the predicate applied to
// the corresponding element of [it2, it2 + distance(it1, last)) returns true
template<class Input1It, class Input2It, class OutputIt, class Predicate>
constexpr OutputIt select_if(Input1It it1, Input1It last,
Input2It it2, OutputIt dest, Predicate pred)
{
for( ; it1 != last; ++it1, ++it2)
{
if (pred(*it2))
{
*dest++ = *it1;
}
}
return dest;
}
template<class Iterator, class Func>
void for_each_n_permute_k(int n, Iterator first, Iterator last, Func f)
{
// e.g. for n == 10 -> {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
std::vector<int> numbers(n);
std::iota(numbers.begin(), numbers.end(), 0);
// e.g. for n == 10 and k == 6 -> {1, 1, 1, 1, 1, 1, 0, 0, 0, 0};
std::vector<int> flags(n);
std::fill(flags.begin(), flags.begin() + std::distance(first, last), 1);
long long int tested = 0;
do
{
// choose the k elements, e.g. for n == 10 and k == 6 -> {0, 1, 2, 3, 4, 5};
select_if(numbers.begin(), numbers.end(), flags.begin(), first,
[] (int x) { return x == 1; });
do
{
++tested;
f();
} while (std::next_permutation(first, last));
// 'flags' starts sorted in descending order, so I need the previous permutation
} while (std::prev_permutation(flags.begin(), flags.end()));
std::cout << "\nPermutations tested: " << tested << '\n';
}
它找到遍历所有且仅遍历唯一的(10!/(10-6)!)= 151200个排列的相同解决方案。
答案 1 :(得分:0)
另一种蛮力方式,但限制了组合的麻烦:
#include <iostream>
#include <algorithm>
int main()
{
int numbers[10] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
int tested_combination_count = 0;
int total_permutation_count = 0;
int last_blue = 0;
do
{
int green = numbers[0];
int yellow = numbers[1];
int purple = numbers[2];
int orange = numbers[3];
int red = numbers[4];
int blue = numbers[5];
++total_permutation_count;
if (last_blue == blue) {
continue;
}
last_blue = blue;
++tested_combination_count;
if (purple * 10 + green == green * yellow
&& purple * 10 + orange == red * red
&& yellow * 10 + orange == red * blue
&& red * 10 + green == green * blue) {
std::cout << green << " " << yellow << " " << purple << " "
<< orange << " " << red << " " << blue << std::endl;
}
} while (std::next_permutation(std::begin(numbers), std::end(numbers)));
std::cout << "Combination tested:" << tested_combination_count
<< " on a total of " << total_permutation_count << std::endl;
}
5 3 1 6 4 9
Combination tested 151192 on a total of 3628800