A:
四维的01背包,注意一下所有代价都是0时的方案输出即可
#include<queue> #include<cstdio> #include<cstdlib> #include<cstring> #include<algorithm> #define maxn 37 using namespace std; int p[maxn],a[maxn],c[maxn],m[maxn],g[maxn]; int dp[maxn][maxn][maxn][maxn],use[maxn]; int n,P,A,C,M; vector <int> mem; int main(){ scanf("%d",&n); int cnt=0; for(int i=1;i<=n;i++) { scanf("%d%d%d%d%d",&p[i],&a[i],&c[i],&m[i],&g[i]); if(p[i]==0&&a[i]==0&&c[i]==0&&m[i]==0) { mem.push_back(i); use[i]=1; } } scanf("%d%d%d%d",&P,&A,&C,&M); dp[0][0][0][0]=0; for(int i=1;i<=n;i++){ if(use[i]==1) continue; for(int j=P;j>=0;j--) for(int k=A;k>=0;k--) for(int t=C;t>=0;t--) for(int l=M;l>=0;l--) if(j>=p[i] && k>=a[i] && t>=c[i] && l>=m[i]){ if(dp[j][k][t][l]<dp[j-p[i]][k-a[i]][t-c[i]][l-m[i]]+g[i]){ dp[j][k][t][l]=dp[j-p[i]][k-a[i]][t-c[i]][l-m[i]]+g[i]; } } } int ans=0,l1=P,l2=A,l3=C,l4=M; for(int j=P;j>=0;j--) for(int k=A;k>=0;k--) for(int t=C;t>=0;t--) for(int l=M;l>=0;l--) if(dp[j][k][t][l]>=ans){ l1=j; l2=k; l3=t; l4=l; ans=dp[j][k][t][l]; } while(1){ int t=233; for(int i=1;i<=n;i++) if(!(p[i]==0 && a[i]==0 && c[i]==0 && m[i]==0) && !use[i] && l1>=p[i] && l2>=a[i] && l3>=c[i] && l4>=m[i] && dp[l1][l2][l3][l4]==dp[l1-p[i]][l2-a[i]][l3-c[i]][l4-m[i]]+g[i]){ use[i]=1; t=i; break; } if(t==233) break; mem.push_back(t); l1-=p[t]; l2-=a[t]; l3-=c[t]; l4-=m[t]; } printf("%d\n",mem.size()); for(int i=0;i<mem.size();i++) printf("%d ",mem[i]-1); return 0; }
C:
E:
#include <cstdio> #include <cstdlib> #include <iostream> #include <cstring> #include <algorithm> #include <cmath> #include <queue> #include <vector> #include <string> #include <map> #include <unordered_map> #define LSON l,m,x<<1 #define RSON m+1,r,x<<1|1 using namespace std; const int MAX=2e6+5; const unsigned long long base = 163; char s[MAX]; unsigned long long p[MAX],hh[MAX]; unordered_map<unsigned long long,int> mp; int cnt; vector<int> L[MAX]; void init(){//处理hh值 p[0] = 1; hh[0] = 0; int n = strlen(s + 1); for(int i = 1; i < MAX/2; i ++) p[i] =p[i-1] * base; for(int i = 1; i <= n; i ++) hh[i] = hh[i - 1] * base + (s[i] - 'a'); } inline unsigned long long get(int l, int r){//取出g里l - r里面的字符串的hh值 return hh[r] - hh[l - 1] * p[r - l + 1]; } inline string read()//inline继续加快速度 { char ch=getchar(); string st1=""; while (!((ch>='a')&&(ch<='z')))//把前面没用的东西去掉,当然,ch在什么范围内可以依据需要修改 ch=getchar(); while ((ch>='a')&&(ch<='z')) st1+=ch,ch=getchar(); return st1;//返回 }//在主程序内可以写st=read(),这样子要读的字符串就到了st内 int main(){ int i,j; char ch; i=0; while((ch=getchar())!=EOF){ s[++i]=ch; } if(s[i]=='\n') i--; int n=i; for(i=n+1;i<=2*n;i++) s[i]=s[i-n]; init(); for(i=1;i<=n;i++){ unsigned long long h=get(i,i+n-1); if(!mp[h]){ mp[h]=++cnt; L[cnt].push_back(i-1); } else L[mp[h]].push_back(i-1); } printf("%d\n",cnt); for(i=1;i<=cnt;i++){ int size=L[i].size(); printf("%d ",size); for(j=0;j<size;j++){ printf("%d%c",L[i][j],j==size-1?'\n':' '); } } return 0; }
H:
随便推推公式就好,发现和小于n/num的质数数量有关,求一求质数数量的前缀和
#include <cstdio> #include <cstdlib> #include <iostream> #include <cstring> #include <algorithm> #include <cmath> #include <queue> #include <vector> #include <string> #include <map> using namespace std; int pri[6000010], cnt; bool flag[10000010]; long long sum[10000010]; void init() { cnt=0; for(int i = 2; i <= 10000000; i ++) { if(!flag[i]) { pri[cnt ++] = i; flag[i] = 1; } for(int j = 0; j < cnt && i * pri[j] <= 10000000; j ++) { flag[i * pri[j]] = 1; if(i % pri[j] == 0) { break; } } } } int main() { int i; init(); for(i=0;i<cnt;i++) sum[pri[i]]++; for(i=0;i<=10000000;i++) sum[i]+=sum[i-1]; int n; scanf("%d",&n); long long ans=0; for(i=1;i<=n;i++) { ans+=sum[n/i]*(sum[n/i]-1); } printf("%lld\n",ans); return 0; }
I:
J: