您的位置:首页 > 其它

hdu1058 & hdu3199

2015-12-19 14:15 309 查看
这两题算同一类型,都是给你几个素数,问只能由这几个素数当做因子的数排列一下,第多少个是?

整体思想都是用已生成的序列是构造新的数。

hdu1058题意:一个数的因子只能是2,3,5,7 ,满足这样条件的数叫humble数,问第多少个是多少。

和紫书上一道丑数 题意近乎一模一样,开始做法就是用优先队列和set判重(后来发现也可以不需要借用set判重)

#include <fstream>
#include <iostream>
#include <string>
#include <complex>
#include <math.h>
#include <set>
#include <vector>
#include <map>
#include <queue>
#include <stdio.h>
#include <stack>
#include <algorithm>
#include <list>
#include <ctime>
#include <memory.h>
#include <ctime>
#include <assert.h>
//#pragma comment(linker, "/STACK:1024000000,1024000000")

#define rep(i,a,n) for (int i=a;i<n;i++)
#define per(i,a,n) for (int i=n-1;i>=a;i--)
#define pb push_back
#define mp make_pair
#define all(x) (x).begin(),(x).end()
#define fi first
#define se second
#define eps 1e-8
#define M_PI 3.141592653589793

typedef long long ll;
const ll mod=1000000007;
const int inf=99999999;
ll powmod(ll a,ll b) {ll res=1;a%=mod;for(;b;b>>=1){if(b&1)res=res*a%mod;a=a*a%mod;}return res;}

using namespace std;
priority_queue<ll,vector<ll>,greater<ll> >q;
set<ll>s;
ll a[]={2,3,5,7};
ll lst[8000];
void Solve()
{
while(!q.empty())q.pop();
q.push(1);
s.insert(1);
int t=0;
while(t<=5942)
{
ll x=q.top();q.pop(); lst[t++]=x;
for(int j=0;j<4;j++){
ll num=x*a[j];
if(!s.count(num)){
s.insert(num);
q.push(num);
}
}
}
}

int main()
{
Solve();
int n;
while(scanf("%d",&n)&&n){
if(n%100==11||n%100==12||n%100==13)  printf("The %dth humble number is %lld.\n",n,lst[n-1]);
else if(n%10==1) printf("The %dst humble number is %lld.\n",n,lst[n-1]);
else if(n%10==2) printf("The %dnd humble number is %lld.\n",n,lst[n-1]);
else if(n%10==3)   printf("The %drd humble number is %lld.\n",n,lst[n-1]);
else printf("The %dth humble number is %lld.\n",n,lst[n-1]);
}
}


这题还有一种思想是每次用选择生成的最小满足条件的数,加入集合,再判断这个数可以从集合里面那个数的下标转移过来,下标++。

体现有序数组的连续性。

#include<bits/stdc++.h>
#define min(a,b) (a<b?a:b)
#define min4(a,b,c,d) min(min(a,b),min(c,d))
using namespace std;
typedef long long ll;
ll dp[6000];
void init()
{
dp[1]=1;
int t=2;
int p1=1,p2=1,p3=1,p4=1;
while(t<=5842){
dp[t++]=min4(dp[p1]*2,dp[p2]*3,dp[p3]*5,dp[p4]*7);
if(dp[t-1]==dp[p1]*2) p1++;
if(dp[t-1]==dp[p2]*3) p2++;
if(dp[t-1]==dp[p3]*5) p3++;
if(dp[t-1]==dp[p4]*7) p4++;
}
}

int main()
{
init();
int n;while(scanf("%d",&n)&&n){
if(n%100!=11&&n%10==1) printf("The %dst humble number is %lld.\n",n,dp
);
else if(n%100!=12&&n%10==2) printf("The %dnd humble number is %lld.\n",n,dp
);
else if(n%100!=13&&n%10==3) printf("The %drd humble number is %lld.\n",n,dp
);
else printf("The %dth humble number is %lld.\n",n,dp
);
}
}


hdu3199

类似的做法。

#include <fstream>
#include <iostream>
#include <string>
#include <cstring>
#include <complex>
#include <math.h>
#include <set>
#include <vector>
#include <map>
#include <queue>
#include <stdio.h>
#include <stack>
#include <algorithm>
#include <list>
#include <ctime>
#include <memory.h>
#include <ctime>
#include <assert.h>

#define rep(i,a,n) for (int i=a;i<n;i++)
#define per(i,a,n) for (int i=n-1;i>=a;i--)
#define pb push_back
#define mp make_pair
#define all(x) (x).begin(),(x).end()
#define fi first
#define se second
#define eps 1e-8
#define M_PI 3.141592653589793

typedef long long ll;
const ll mod=1000000007;
const int inf=99999999;
ll powmod(ll a,ll b) {ll res=1;a%=mod;for(;b;b>>=1){if(b&1)res=res*a%mod;a=a*a%mod;}return res;}

using namespace std;
ll dp[110000];
int n;
ll solve(ll a,ll b,ll c)
{
memset(dp,0,sizeof(dp));
dp[0]=1;
int t=1,p1=0,p2=0,p3=0;
while(t<=n+1)
{
dp[t++]=min(dp[p1]*a,min(dp[p2]*b,dp[p3]*c));
if(dp[p1]*a==dp[t-1]) p1++;
if(dp[p2]*b==dp[t-1]) p2++;
if(dp[p3]*c==dp[t-1]) p3++;
}
return dp
;
}

int main()
{
ll a,b,c;
while(~scanf("%lld %lld %lld %d",&a,&b,&c,&n)){
printf("%lld\n",solve(a,b,c));
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  dp-STL