nt错误大全
T1质数和分解
题目传送门
题目描述
任何大于 1的自然数 n 都可以写成若干个大于等于 2 且小于等于 n的质数之和表达式(包括只有一个数构成的和表达式的情况),并且可能有不止一种质数和的形式。
这里所谓两个本质相同的表达式是指可以通过交换其中一个表达式中参加和运算的各个数的位置而直接得到另一个表达式。
试编程求解自然数 n 可以写成多少种本质不同的质数和表达式。
输入格式:文件中的每一行存放一个自然数 n(2≤n≤200)
输出格式:依次输出每一个自然数 n 的本质不同的质数和表达式的数目。
注意:多组输入
思路:可以看出来,本题的状态转移方程是 f[j]+=f[j-s[i]]
f[i]表示i可以分解成多少个本质不同的质数表达式
f[0]=1//初始化
f[1]=0//1不是质数
f[2]=1//质因数:2
f[3]=1//质因数:3
f[4]=1//质因数:2
f[5]=2// 5=5=2+3
f[6]=2// 6=2+2+2 =3+3 注意:6=1+5是错误方案!1不是素数!
f[7]=3// 7 =7 【7自身也是质数】=2+(7-2)【那么开始分解5】=2+5 =2+2+3
由此可得,假设把j分解成s[i]+(j-s[i])的形式,那么原题可变化为j-s[i]可以分解成多少个本质不同的质数表达式,同理j-s[i]可以继续分解。
初始化!!f[0]=1!
#include <iostream>
#include <cstdio>
using namespace std;
int a,prime[50]={0,2,3,5,7,11,13,17,19,23,29,31,37,41,43,47,53,59,61,67,71,73,79,83,89,97,101,103,107,109,113,127,131,137,139,149,151,157,163,167,173,179,181,191,193,197,199};
int main()
{
while(cin>>a)
{
int dp[242]={1};
for(int i=1;i<=46;i++)
{
for(int j=prime[i];j<=200;j++)
dp[j]+=dp[j-prime[i]];
}
cout<<dp[a]<<endl;
}
return 0;
}
T2暗黑游戏——水题
#include<bits/stdc++.h>
using namespace std;
const int maxn=505;
int n,pg,ru;
int p[maxn],r[maxn],num[maxn],val[maxn];
int dp[205][205];
int main()
{
scanf("%d%d%d",&n,&pg,&ru);
for(int i=1;i<=n;++i)
{
scanf("%d%d%d%d",&p[i],&r[i],&num[i],&val[i]);
}
for(int i=1;i<=n;++i)
{
if(num[i]==0)//完全背包
{
for(int j=0;j<=pg;++j)
{
for(int k=0;k<=ru;++k)
{
if(j>=p[i]&&k>=r[i])
{
dp[j][k]=max(dp[j][k],dp[j-p[i]][k-r[i]]+val[i]);
}
}
}
}
else
{//01和多重
for(int j=1;j<=num[i];++j)
{
for(int k=pg;k>=p[i];--k)
{
for(int t=ru;t>=r[i];--t)
{
dp[k][t]=max(dp[k][t],dp[k-p[i]][t-r[i]]+val[i]);
}
}
}
}
}
printf("%d",dp[pg][ru]);
return 0;
}
T3逃亡的准备
【问题描述】
在《Harry Potter and the Deathly Hallows》中,Harry Potter他们一起逃亡,现在有许多的东西要放到赫敏的包里面,但是包的大小有限,所以我们只能够在里面放入非常重要的物品,现在给出该种物品的数量、体积、价值的数值,希望你能够算出怎样能使背包的价值最大的组合方式,并且输出这个数值,赫敏会非常地感谢你。
【输入文件】(hallows.in)
(1)第一行有2个整数,物品种数n和背包装载体积v。
(2)2行到n+1行每行3个整数,为第i种物品的数量m、体积w、价值s。.
【输出文件】(hallows.out)
输出文件hallows.out仅包含一个整数,即为能拿到的最大的物品价值总和。
#include<bits/stdc++.h>
typedef long long ll;
const int maxn=6005;
using namespace std;
int dp[maxn];
int n,v;
int num[maxn],wei[maxn],val[maxn];
int main()
{
scanf("%d%d",&n,&v);
for(int i=1;i<=n;++i)
{
scanf("%d%d%d",&num[i],&wei[i],&val[i]);
}
for(int i=1;i<=n;++i)
{
for(int j=v;j>=0;--j)
{
for(int k=0;k<=num[i];++k)
{
//if(j-k*wei[i]>=0)
if(j<k*wei[i])break;//如果超了就break,有效减小复杂度!!
dp[j]=max(dp[j],dp[j-k*wei[i]]+k*val[i]);
}
}
}
printf("%d",dp[v]);
return 0;
}