题目
题目来自csdn每日一刷
如上图六角星,有12个孔,每个孔按上面编号,各填入不重复的1~12个数,并使每条线的上的总和相等。要求输入前3个数字后,生成剩余的数字。
结果
input 3 nums:1 8 2
FIND the res:
1 8 2 9 7 11 10 12 3 5 6 4
each line num is:
26 26 26 26 26 26
input 3 nums:5 9 1
FIND the res:
5 9 1 4 5 3 6 10 2 3 4 5
each line num is:
19 19 19 19 19 19
代码
思路,使用递归 ,前项遍历确定后,再遍历后一项
#include
const int one_line_count = 4;
const int line_count = 6;
const int index_count = one_line_count * line_count;
int line_indexes[] = {
2, 3, 4, 5,
1, 3, 6, 8,
1, 4, 7, 11,
8, 9, 10 ,11,
2, 6, 9, 12,
5, 7, 10, 12
};
const int num_count = 12;
bool _fill_six_angle(int* num_in_hole, int step) {
if (step >= num_count) {
// 计算所有线是否相等
int old_total = 0;
for (int i = 0; i < line_count; ++i) {
int cur_total = 0;
for (int j = 0; j < one_line_count; ++j) {
int ci = i * one_line_count + j;
int ti = line_indexes[ci] -1;
cur_total += num_in_hole[ti];
}
if (old_total != 0 && old_total != cur_total)
return false;
old_total = cur_total;
}
return true;
}
// 从12个数字里遍历
for (int j = 0; j < num_count; ++j) {
// 不能跟前面的数字相同
for (int k = 0; k < step; ++k) {
if (num_in_hole[k] == j + 1) {
++j;
}
}
if (j >= num_count)
return false;
num_in_hole[step] = j + 1;
// 遍历后面
if (_fill_six_angle(num_in_hole, step + 1))
return true;
}
return false;
}
void fill_six_angle(int* pre_nums, int pre_count) {
int num_in_hole[num_count]; // 编号对应的数字
memset(num_in_hole, 0, sizeof(num_in_hole));
memcpy(num_in_hole, pre_nums, sizeof(int) * pre_count);
bool res = _fill_six_angle(num_in_hole, pre_count);
if (res) {
std::cout << "FIND the res: " << std::endl;
for (int i = 0; i < num_count; ++i) {
std::cout << " " << num_in_hole[i];
}
std::cout << std::endl << "each line num is:" << std::endl;
for (int i = 0; i < line_count; ++i) {
int cur_total = 0;
for (int j = 0; j < one_line_count; ++j) {
int ci = i * one_line_count + j;
int ti = line_indexes[ci] - 1;
cur_total += num_in_hole[ti];
}
std::cout << " " <<cur_total;
}
}
else {
std::cout << "FAIL to get the result!!" << std::endl;
}
}