数字三角形(洛谷-P1118)
题目描述
FJ
and his cows enjoy playing a mental game. They write down the numbers from 11 to N(1 ≤ N ≤ 10) in a certain order and then sum adjacent numbers to produce a new list with one fewer number. They repeat this until only a single number is left. For example, one instance of the game (when N=4) might go like this:
3 1 2 4
4 3 6
7 9
16
Behind FJ
's back, the cows have started playing a more difficult game, in which they try to determine the starting sequence from only the final total and the number N . Unfortunately, the game is a bit above FJ
's mental arithmetic capabilities.
Write a program to help FJ
play the game and keep up with the cows.
有这么一个游戏:
写出一个 1 至 N的排列 a_i,然后每次将相邻两个数相加,构成新的序列,再对新序列进行这样的操作,显然每次构成的序列都比上一次的序列长度少 1,直到只剩下一个数字位置。下面是一个例子:
3,1,2,4
4,3,6
7,9
16
最后得到 16 这样一个数字。
现在想要倒着玩这样一个游戏,如果知道 N,知道最后得到的数字的大小 sum,请你求出最初序列 a_i,为 1 至 N 的一个排列。若答案有多种可能,则输出字典序最小的那一个。
管理员注:本题描述有误,这里字典序指的是 1,2,3,4,5,6,7,8,9,10,11,12
而不是 1,10,11,12,2,3,4,5,6,7,8,9
输入输出格式
输入格式:
两个正整数 n,sum 。
输出格式:
输出包括 1 行,为字典序最小的那个答案。
当无解的时候,请什么也不输出。
输入输出样例
输入样例#1:
4 16
输出样例#1:
3 1 2 4
———————————————————————————————————————————————————————
思路:
一开始毫无思路,看了题解知道答案的系数和与杨辉三角有关,于是先用一个数组存储答案,再用dfs搜索。
最后两个测试点超时,仔细看了看代码,发现可以用剪枝,剪枝后成功AC。
注:关于答案系数与杨辉三角
源代码
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<string>
#include<cstdlib>
#include<queue>
#include<set>
#include<map>
#include<stack>
#include<vector>
#define INF 0x3f3f3f3f
#define PI acos(-1.0)
#define N 21
#define MOD 123
#define E 1e-6
using namespace std;
int n,sum;
int triangle[N][N];
int a[N],vis[N];
bool flag;
void dfs(int step,int cnt)
{
if(flag)
return;
if(cnt>sum)//当前和大于sum,剪枝
return;
if(step==n+1&&cnt==sum)//达到最后一层并找到答案
{
flag=true;
for(int i=1;i<=n;i++)
cout<<a[i]<<" ";
}
for(int i=1;i<=n;i++)
if(!vis[i])
{
a[step]=i;
vis[i]=1;
cnt+=triangle[n][step]*a[step];//加上i*系数
dfs(step+1,cnt);
cnt-=triangle[n][step]*a[step];//减去i*系数
vis[i]=0;
}
}
int main()
{
cin>>n>>sum;
/*构造存储答案系数的杨辉三角*/
triangle[1][1]=1;
for(int i=2;i<=n;i++)
for(int j=1;j<=i;j++)
triangle[i][j]=triangle[i-1][j-1]+triangle[i-1][j];
dfs(1,0);//从1开始搜索
return 0;
}
推荐阅读
-
P1216 [USACO1.5][IOI1994]数字三角形 Number Triangles(洛谷)
-
数字三角形(洛谷-P1118)
-
统计范围内不含'7'的数字个数(洛谷P1590题题解,Java语言描述)
-
洛谷P4013 数字梯形问题(费用流)
-
洛谷P1829 [国家集训队]Crash的数字表格 / JZPTAB(莫比乌斯反演)
-
【洛谷】P1118数字三角形
-
洛谷P1829 [国家集训队]Crash的数字表格 / JZPTAB(莫比乌斯反演)
-
【洛谷】P1118 [USACO06FEB]数字三角形`Backward Digit Su (题解)
-
按字母位置关系给数字排序(洛谷P4414题题解,Java语言描述)
-
洛谷P4013 数字梯形问题(费用流)