zoukankan      html  css  js  c++  java
  • 第六周 10.4-10.10

    10.4

    CF 582A GCD Table

    贪心取最大。熟悉set大法。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 #include <vector>
     6 #include <set>
     7 using namespace std;
     8 multiset<int> S;
     9 multiset<int>::iterator it;
    10 vector<int> ans;
    11 
    12 int gcd(int a,int b)
    13 {
    14     return a%b?gcd(b,a%b):b;
    15 }
    16 
    17 int main(void)
    18 {
    19     S.clear();
    20     int n; scanf("%d",&n);
    21     for(int i=0;i<n*n;i++)
    22     {
    23         int x;
    24         scanf("%d",&x);
    25         S.insert(x);
    26     }
    27     while(!S.empty())
    28     {
    29         it=S.end(); it--;
    30         int cur=*it;
    31         S.erase(it);
    32         for(int i=0;i<ans.size();i++)
    33         {
    34             int t=gcd(ans[i],cur);
    35             for(int i=0;i<2;i++)
    36             {
    37                 it=S.find(t);
    38                 S.erase(it);
    39             }
    40         }
    41         ans.push_back(cur);
    42     }
    43     for(int i=0;i<ans.size();i++) printf("%d ",ans[i]);
    44     puts("");
    45     return 0;
    46 }
    Aguin

    HDU 3713 Double Maze

    BFS。手写队列保存前驱输出路径。

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <algorithm>
      5 using namespace std;
      6 bool vis[7][7][7][7];
      7 int G[21][7][7];
      8 
      9 struct node
     10 {
     11     int x1,y1,x2,y2;
     12     char op;
     13     int pre;
     14 }p[2000];
     15 
     16 bool f(int op,int i,int j,int x)
     17 {
     18     return G[op][i][j]&(1<<(x-1));
     19 }
     20 
     21 void ans_print(int pos)
     22 {
     23     if(p[pos].pre) ans_print(p[pos].pre);
     24     putchar(p[pos].op);
     25     return;
     26 }
     27 
     28 int main(void)
     29 {
     30     int T; cin>>T;
     31     for(int i=1;i<=6;i++) for(int j=1;j<=6;j++) scanf("%d",&G[0][i][j]);
     32     for(int t=1;t<T;t++)
     33     {
     34         int xs1,ys1,xs2,ys2,xt1,yt1,xt2,yt2;
     35         for(int i=1;i<=6;i++) for(int j=1;j<=6;j++)
     36         {
     37             scanf("%d",&G[t][i][j]);
     38             if(f(t-1,i,j,6)){xs1=i;ys1=j;}
     39             if(f(t,i,j,6)){xs2=i;ys2=j;}
     40             if(f(t-1,i,j,7)){xt1=i;yt1=j;}
     41             if(f(t,i,j,7)){xt2=i;yt2=j;}
     42         }
     43         int cnt=0,start=-1,ans=-1;
     44         memset(vis,0,sizeof(vis));
     45         p[0].x1=xs1,p[0].y1=ys1,p[0].x2=xs2,p[0].y2=ys2;
     46         vis[xs1][ys1][xs2][ys2]=1;
     47         while(start<cnt)
     48         {
     49             int pos=++start;
     50             int x1=p[pos].x1,y1=p[pos].y1,x2=p[pos].x2,y2=p[pos].y2;
     51             if(x1==xt1&&y1==yt1&&x2==xt2&&y2==yt2) {ans=pos; break;}
     52             if((f(t-1,x1,y1,2)||(x1<6&&f(t-1,x1+1,y1,5)))&&(f(t,x2,y2,2)||(x2<6&&f(t,x2+1,y2,5))))
     53             {
     54                 int xx1=x1+(f(t-1,x1,y1,2)?0:1),xx2=x2+(f(t,x2,y2,2)?0:1);
     55                 if(!vis[xx1][y1][xx2][y2])
     56                 {
     57                     cnt++;
     58                     p[cnt].x1=xx1,p[cnt].y1=y1,p[cnt].x2=xx2,p[cnt].y2=y2;
     59                     p[cnt].op='D',p[cnt].pre=pos;
     60                     vis[xx1][y1][xx2][y2]=1;
     61                 }
     62             }
     63             if((f(t-1,x1,y1,1)||(y1>1&&f(t-1,x1,y1-1,5)))&&(f(t,x2,y2,1)||(y2>1&&f(t,x2,y2-1,5))))
     64             {
     65                 int yy1=y1-(f(t-1,x1,y1,1)?0:1),yy2=y2-(f(t,x2,y2,1)?0:1);
     66                 if(!vis[x1][yy1][x2][yy2])
     67                 {
     68                     cnt++;
     69                     p[cnt].x1=x1,p[cnt].y1=yy1,p[cnt].x2=x2,p[cnt].y2=yy2;
     70                     p[cnt].op='L',p[cnt].pre=pos;
     71                     vis[x1][yy1][x2][yy2]=1;
     72                 }
     73             }
     74             if((f(t-1,x1,y1,3)||(y1<6&&f(t-1,x1,y1+1,5)))&&(f(t,x2,y2,3)||(y2<6&&f(t,x2,y2+1,5))))
     75             {
     76                 int yy1=y1+(f(t-1,x1,y1,3)?0:1),yy2=y2+(f(t,x2,y2,3)?0:1);
     77                 if(!vis[x1][yy1][x2][yy2])
     78                 {
     79                     cnt++;
     80                     p[cnt].x1=x1,p[cnt].y1=yy1,p[cnt].x2=x2,p[cnt].y2=yy2;
     81                     p[cnt].op='R',p[cnt].pre=pos;
     82                     vis[x1][yy1][x2][yy2]=1;
     83                 }
     84             }
     85             if((f(t-1,x1,y1,4)||(x1>1&&f(t-1,x1-1,y1,5)))&&(f(t,x2,y2,4)||(x2>1&&f(t,x2-1,y2,5))))
     86             {
     87                 int xx1=x1-(f(t-1,x1,y1,4)?0:1),xx2=x2-(f(t,x2,y2,4)?0:1);
     88                 if(!vis[xx1][y1][xx2][y2])
     89                 {
     90                     cnt++;
     91                     p[cnt].x1=xx1,p[cnt].y1=y1,p[cnt].x2=xx2,p[cnt].y2=y2;
     92                     p[cnt].op='U',p[cnt].pre=pos;
     93                     vis[xx1][y1][xx2][y2]=1;
     94                 }
     95             }
     96         }
     97         if(ans<0) printf("-1");
     98         else if(ans>0) ans_print(ans);
     99         puts("");
    100     }
    101     return 0;
    102 }
    Aguin

    10.5

    POJ 3573 I18n

    set大法。

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <algorithm>
      5 #include <set>
      6 using namespace std;
      7 char s[200];
      8 
      9 struct node
     10 {
     11     char l,r;
     12     int mid;
     13     bool ok;
     14     char word[100];
     15     friend bool operator < (node x,node y)
     16     {
     17         if(x.l!=y.l) return x.l<y.l;
     18         if(x.mid!=y.mid) return x.mid<y.mid;
     19         return x.r<y.r;
     20     }
     21 };
     22 set<node> S;
     23 set<node>::iterator it;
     24 
     25 bool is_alp(char c)
     26 {
     27     return (c>='a'&&c<='z') || (c>='A'&&c<='Z');
     28 }
     29 
     30 bool is_num(char c)
     31 {
     32     return c>='0'&&c<='9';
     33 }
     34 
     35 char lower(char c)
     36 {
     37     return (c<='Z')?(c+32):c;
     38 }
     39 
     40 char upper(char c)
     41 {
     42     return (c>='a')?(c-32):c;
     43 }
     44 
     45 int main(void)
     46 {
     47     while(gets(s))
     48     {
     49         int len=strlen(s);
     50         for(int i=0;i<len;i++)
     51         {
     52             if(is_alp(s[i]))
     53             {
     54                 if(i==len-1) putchar(s[i]);
     55                 else if(is_alp(s[i+1]))
     56                 {
     57                     int L=0;
     58                     while(i+L<len && is_alp(s[i+L])) L++;
     59                     if(L==2||L==3) {putchar(s[i]); continue;}
     60                     node tmp;
     61                     tmp.l=lower(s[i]);
     62                     tmp.r=lower(s[i+L-1]);
     63                     tmp.mid=L-2;
     64                     tmp.ok=1;
     65                     for(int j=0;j<L;j++) tmp.word[j]=lower(s[i+j]);
     66                     tmp.word[L]=0;
     67                     if((it=S.find(tmp))!=S.end())
     68                     {
     69                         if((*it).ok&&strcmp((*it).word,tmp.word)!=0)
     70                         {
     71                             S.erase(it);
     72                             tmp.ok=0;
     73                             S.insert(tmp);
     74                         }
     75                     }
     76                     else S.insert(tmp);
     77                     for(int j=0;j<L;j++) putchar(s[i+j]);
     78                     i+=L-1;
     79                 }
     80                 else if(is_num(s[i+1]))
     81                 {
     82                     int L;
     83                     node tmp;
     84                     tmp.l=lower(s[i]);
     85                     if(is_num(s[i+2]))
     86                     {
     87                         tmp.mid=10*(s[i+1]-'0')+s[i+2]-'0';
     88                         tmp.r=lower(s[i+3]);
     89                         L=4;
     90                     }
     91                     else
     92                     {
     93                         tmp.mid=s[i+1]-'0';
     94                         tmp.r=lower(s[i+2]);
     95                         L=3;
     96                     }
     97                     if((it=S.find(tmp))!=S.end()&&(*it).ok)
     98                     {
     99                         int type=(s[i]<='Z')+(s[i+L-1]<='Z');
    100                         int L=strlen((*it).word);
    101                         if(type==0) for(int j=0;j<L;j++) putchar((*it).word[j]);
    102                         else if(type==1)
    103                         {
    104                             putchar(upper((*it).word[0]));
    105                             for(int j=1;j<L;j++) putchar((*it).word[j]);
    106                         }
    107                         else for(int j=0;j<L;j++) putchar(upper((*it).word[j]));
    108                     }
    109                     else for(int j=0;j<L;j++) putchar(s[i+j]);
    110                     i+=L-1;
    111                 }
    112                 else putchar(s[i]);
    113             }
    114             else putchar(s[i]);
    115         }
    116         puts("");
    117     }
    118     return 0;
    119 }
    Aguin

    POJ 3974 Palindrome

    重贴板。温习manacher。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 const int maxn=1001000;
     7 char s[maxn],b[2*maxn],E[]="END";
     8 int p[2*maxn];
     9 
    10 int main(void)
    11 {
    12     int kase=0;
    13     while(~scanf("%s",s))
    14     {
    15         if(strcmp(s,E)==0) break;
    16         int m=strlen(s),len=2*m+1;
    17         b[0]='!'; b[len+1]='@';
    18         b[len]='#';
    19         for(int i=0;i<m;i++)
    20         {
    21             b[2*i+2]=s[i];
    22             b[2*i+1]='#';
    23         }
    24         int mx=0,id;
    25         for(int i=1;i<=len;i++)
    26         {
    27             if(mx>i) p[i]=min(p[2*id-i],mx-i);
    28             else p[i]=1;
    29             while(b[i+p[i]]==b[i-p[i]]) p[i]++;
    30             if(p[i]+i>mx) {mx=p[i]+i; id=i;}
    31         }
    32         int M=0;
    33         for(int i=1;i<=len;i++) M=max(M,p[i]);
    34         printf("Case %d: %d
    ",++kase,M-1);
    35     }
    36     return 0;
    37 }
    Aguin

    HDU 5413 吉哥系列故事――完美队形II

    吐槽题名。先manacher再处理下连续单调个数。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 const int maxn=101000;
     7 int b[2*maxn],p[2*maxn];
     8 int inc[maxn],des[maxn];
     9 
    10 int main(void)
    11 {
    12     int T; cin>>T;
    13     while(T--)
    14     {
    15         int n; scanf("%d",&n);
    16         int len=2*n+1;
    17         b[0]=-1; b[len+1]=-2;
    18         b[len]=-3;
    19         for(int i=0;i<n;i++)
    20         {
    21             scanf("%d",b+2*i+2);
    22             b[2*i+1]=-3;
    23         }
    24         int mx=0,id;
    25         for(int i=1;i<=len;i++)
    26         {
    27             if(mx>i) p[i]=min(p[2*id-i],mx-i);
    28             else p[i]=1;
    29             while(b[i+p[i]]==b[i-p[i]]) p[i]++;
    30             if(p[i]+i>mx) {mx=p[i]+i; id=i;}
    31         }
    32         inc[1]=des[n]=1;
    33         for(int i=2;i<n;i++) inc[i]=(b[2*i]>=b[2*i-2])?(inc[i-1]+1):1;
    34         for(int i=n-1;i>0;i--) des[i]=(b[2*i]>=b[2*i+2])?(des[i+1]+1):1;
    35         int ans=0;
    36         for(int i=1;i<=len;i++)
    37         {
    38             int tmp;
    39             if(i%2==0) tmp=min(p[i]-1,2*min(inc[i/2],des[i/2])-1);
    40             else tmp=min(p[i]-1,2*min(inc[i/2],des[i/2+1]));
    41             ans=max(ans,tmp);
    42         }
    43         printf("%d
    ",ans);
    44     }
    45     return 0;
    46 }
    Aguin

    HDU 3294 Girls' research

    水manacher。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 const int maxn=201000;
     7 char a[5],s[maxn],b[2*maxn];
     8 int p[2*maxn];
     9 
    10 char f(char c)
    11 {
    12     c=c-a[0]+'a';
    13     if(c<'a') c+=26;
    14     return c;
    15 }
    16 
    17 int main(void)
    18 {
    19     while(~scanf("%s",a))
    20     {
    21         scanf("%s",s);
    22         int m=strlen(s),len=2*m+1;
    23         b[0]='!'; b[len+1]='@';
    24         b[len]='#';
    25         for(int i=0;i<m;i++)
    26         {
    27             b[2*i+2]=s[i];
    28             b[2*i+1]='#';
    29         }
    30         int mx=0,id;
    31         for(int i=1;i<=len;i++)
    32         {
    33             if(mx>i) p[i]=min(p[2*id-i],mx-i);
    34             else p[i]=1;
    35             while(b[i+p[i]]==b[i-p[i]]) p[i]++;
    36             if(p[i]+i>mx) {mx=p[i]+i; id=i;}
    37         }
    38         int M=0,pos;
    39         for(int i=1;i<=len;i++)
    40             if(p[i]-1>M) {M=p[i]-1; pos=i;}
    41         if(M<=1) puts("No solution!");
    42         else
    43         {
    44             printf("%d %d
    ",(pos-p[pos]+2)/2-1,(pos+p[pos]-2)/2-1);
    45             for(int i=pos-p[pos]+2;i<=pos+p[pos]-2;i+=2) putchar(f(b[i]));
    46             puts("");
    47         }
    48     }
    49     return 0;
    50 }
    Aguin

    HDU 4763 Theme Section

    exkmp。暴力一下。

     1 # include <iostream>
     2 # include <cstdio>
     3 # include <cstring>
     4 # include <algorithm>
     5 using namespace std;
     6 # define maxn 1000010
     7 int m,Next[maxn];
     8 char b[maxn];
     9 
    10 void getNext(void)
    11 {
    12     int P=1,j; Next[0]=m;
    13     for(int i=Next[1]=0;i<m-1&&b[i]==b[i+1];) Next[1]=++i;
    14     for(int i=2;i<m;i++)
    15     {
    16         if(Next[i-P]+i<Next[P]+P) Next[i]=Next[i-P];
    17         else
    18         {
    19             j=max(Next[P]+P-i,0);
    20             while(i+j<m&&b[j]==b[j+i]) j++;
    21             Next[i]=j; P=i;
    22         }
    23     }
    24     return;
    25 }
    26 
    27 int main(void)
    28 {
    29     int T; cin>>T;
    30     while(T--)
    31     {
    32         scanf("%s",b);
    33         m=strlen(b);
    34         getNext();
    35         int ans=0;
    36         for(int i=1;i<=m/3;i++)
    37         {
    38             if(Next[m-i]!=i) continue;
    39             int ok=0;
    40             for(int j=i;j<=m-2*i;j++)
    41             if(Next[j]>=i) {ok=1;break;}
    42             if(ok) ans=i;
    43         }
    44         printf("%d
    ",ans);
    45     }
    46     return 0;
    47 }
    Aguin

     终于切完1个月前开的一版。其实到最后根本不想做了。

    10.6

    POJ 1200 Crazy Search

    题目都没给范围阿。哈希还是不怎么懂- -

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 using namespace std;
     5 bool Hash[16000000];
     6 char s[10000000];
     7 int c[256];
     8 
     9 int main(void)
    10 {
    11     int N,NC;
    12     scanf("%d%d%s",&N,&NC,s);
    13     int cnt=0,len=strlen(s);
    14     if(N>len) {puts("0");return 0;}
    15     for(int i=0;i<len;i++)
    16     {
    17         if(!c[s[i]]) c[s[i]]=++cnt;
    18         if(cnt==NC) break;
    19     }
    20     int sum=0,tmp=1;
    21     for(int i=0;i<N;i++)
    22     {
    23         sum=sum*NC+c[s[i]]-1;
    24         tmp*=NC;
    25     }
    26     tmp/=NC; Hash[sum]=1;
    27     int ans=1;
    28     for(int i=N;i<len;i++)
    29     {
    30         sum-=(c[s[i-N]]-1)*tmp;
    31         sum*=NC;
    32         sum+=c[s[i]]-1;
    33         if(!Hash[sum]) {ans++;Hash[sum]=1;}
    34     }
    35     printf("%d
    ",ans);
    36     return 0;
    37 }
    Aguin

    CF 584 C Marina and Vasya

    补题。分类讨论。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 const int maxn=1e5+10;
     7 char a[maxn],b[maxn],c[maxn];
     8 
     9 char no(char a)
    10 {
    11     for(char i='a';i<='z';i++)
    12         if(i!=a) return i;
    13 }
    14 
    15 char no(char a,char b)
    16 {
    17     for(char i='a';i<='z';i++)
    18         if(i!=a&&i!=b) return i;
    19 }
    20 
    21 int main(void)
    22 {
    23     int n,t;
    24     scanf("%d%d",&n,&t);
    25     scanf("%s%s",a,b);
    26     int len=strlen(a),same=0;
    27     for(int i=0;i<len;i++) same+=(a[i]==b[i]);
    28     int dif=len-same,ok;
    29     if((dif+1)/2>t) ok=0;
    30     else
    31     {
    32         ok=1;
    33         int p=max(0,t-dif),q=dif-min(t,dif),r=min(t,dif)-q;
    34         for(int i=0;i<len;i++)
    35         {
    36             if(a[i]==b[i])
    37             {
    38                 if(p) {c[i]=no(a[i]);p--;}
    39                 else c[i]=a[i];
    40             }
    41             else
    42             {
    43                 if(r){r--; c[i]=no(a[i],b[i]);}
    44                 else if(q) {q--; c[i]=a[i];}
    45                 else c[i]=b[i];
    46             }
    47         }
    48     }
    49     if(ok) for(int i=0;i<len;i++) putchar(c[i]);
    50     else printf("-1");
    51     puts("");
    52     return 0;
    53 }
    Aguin

    10.7

    UESTC 88 Fold The Paper

    暴搜20那边。500那边dp。

    状态dp[i][cur]表示前i个中取的最后一个为奇(cur=1)或偶(cur=0)的最大值。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 const int INF=2e8;
     7 int sum[510],dp[510][2];
     8 int num[21][510];
     9 int choose[21];
    10 int N,M;
    11 
    12 bool judge(int x)
    13 {
    14     int last=0;
    15     for(int i=1;i<=N;i++)
    16     {
    17         if(x&(1<<(i-1)))
    18         {
    19             choose[i]=1;
    20             if(last&&!((i-last)&1)) return false;
    21             last=i;
    22         }
    23         else choose[i]=0;
    24     }
    25     return true;
    26 }
    27 
    28 void getsum(void)
    29 {
    30     memset(sum,0,sizeof(sum));
    31     for(int i=1;i<=N;i++) if(choose[i])
    32         for(int j=1;j<=M;j++)
    33             sum[j]+=num[i][j];
    34     return;
    35 }
    36 
    37 int main(void)
    38 {
    39     dp[0][0]=dp[0][1]=-INF;
    40     int T ; cin>>T;
    41     for(int kase=1;kase<=T;kase++)
    42     {
    43         scanf("%d%d",&N,&M);
    44         for(int i=1;i<=N;i++)
    45             for(int j=1;j<=M;j++)
    46                 scanf("%d",&num[i][j]);
    47         int ans=-INF;
    48         for(int i=1;i<(1<<N);i++)
    49         {
    50             if(!judge(i)) continue;
    51             getsum();
    52             for(int j=1;j<=M;j++)
    53             {
    54                 int cur=j&1;
    55                 dp[j][cur]=max(sum[j],max(dp[j-1][cur^1]+sum[j],dp[j-1][cur]));
    56                 dp[j][cur^1]=dp[j-1][cur^1];
    57             }
    58             ans=max(ans,max(dp[M][0],dp[M][1]));
    59         }
    60         printf("Case #%d: %d
    ",kase,ans);
    61     }
    62     return 0;
    63 }
    Aguin

    CF 584 D Dima and Lisa

    暴力。有两个知识点。

    1.哥德巴赫猜想。

    2.1e9内相邻的素数差<300。

     1 #include <iostream>
     2 #include <cstdio>
     3 using namespace std;
     4 
     5 bool is_prime(int x)
     6 {
     7     if(x<=1) return false;
     8     for(int i=2;i*i<=x;i++)
     9         if(x%i==0) return false;
    10     return true;
    11 }
    12 
    13 int main(void)
    14 {
    15     int a,b,c=0;
    16     scanf("%d",&a);
    17     if(is_prime(a)) printf("1
    %d
    ",a);
    18     else
    19     {
    20         b=a-2;
    21         while(!is_prime(b)) b--;
    22         a-=b;
    23         if(is_prime(a)) printf("2
    %d %d
    ",a,b);
    24         else
    25         {
    26             while(!is_prime(a)||!is_prime(c)) c++,a--;
    27             printf("3
    %d %d %d
    ",a,b,c);
    28         }
    29     }
    30     return 0;
    31 }
    Aguin

    CF 584 E Anton and Ira

    最小cost就是每个字符在两个串中的距离差之和。

    移动时只要保证每个字符都不做多余的移动即可。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <algorithm>
     4 #include <vector>
     5 using namespace std;
     6 typedef pair<int,int> pii;
     7 const int maxn=3000;
     8 int p[maxn],s[maxn];
     9 int pp[maxn],ps[maxn];
    10 vector<pii> ans;
    11 
    12 int main(void)
    13 {
    14     int n; scanf("%d
    ",&n);
    15     for(int i=1;i<=n;i++)
    16     {
    17         scanf("%d",p+i);
    18         pp[p[i]]=i;
    19     }
    20     for(int i=1;i<=n;i++)
    21     {
    22         scanf("%d",s+i);
    23         ps[s[i]]=i;
    24     }
    25     int cost=0;
    26     for(int i=1;i<=n;i++) while(p[i]!=s[i])
    27     {
    28         int x=s[i],px=pp[x],py=px-1,y=p[py];
    29         while(ps[y]<px) {py--;y=p[py];}
    30         swap(p[px],p[py]);
    31         swap(pp[x],pp[y]);
    32         ans.push_back(pii(px,py));
    33         cost+=px-py;
    34     }
    35     printf("%d
    %d
    ",cost,ans.size());
    36     for(int i=0;i<ans.size();i++) printf("%d %d
    ",ans[i].first,ans[i].second);
    37     return 0;
    38 }
    Aguin

    10.9

    秘制蛙。

    10.10

    UESCT 86 Divide

    原理上是简单贪心。处理上有技巧。

    先把所有物品保存在sum[]里。再处理进位。

    处理进位的时候在carry[]里标记某一位能否由比它小的物品组合凑成。

    再从最高位往后扫一遍。

    如果一个物品是偶数件。它必然能等分。

    如果一个物品能被比它小的物品凑成。

    i)如果它是奇数个。加上凑成的一件正好等分。

    ii)如果它是偶数个。凑成的那一件必然能拆成两个半个(因为所有都是2^ai大小)。也能等分。

    所以扫到第一个个数为奇数且不能由比它小的物品凑成的物品时。就能计算答案了。

    答案就是这件物品减去所有比它小的物品。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 typedef long long LL;
     7 const int maxn=111111;
     8 int carry[maxn];
     9 LL sum[maxn];
    10 
    11 int main(void)
    12 {
    13     int T; cin>>T;
    14     for(int kase=1;kase<=T;kase++)
    15     {
    16         int N; scanf("%d",&N);
    17         int st=0;
    18         memset(sum,0,sizeof(sum));
    19         for(int i=0;i<N;i++)
    20         {
    21             int a,x;
    22             scanf("%d%d",&a,&x);
    23             sum[a]+=(LL)x;
    24             st=max(st,a);
    25         }
    26         memset(carry,0,sizeof(carry));
    27         for(int i=0;i<=st;i++)
    28         {
    29             if(sum[i]/2) carry[i+1]=1;
    30             sum[i+1]+=sum[i]/2;
    31             sum[i]%=2;
    32         }
    33         while(st&&(!sum[st]||carry[st])) st--;
    34         printf("Case #%d: ",kase);
    35         if(!st) printf("%d",sum[st]);
    36         else
    37         {
    38             for(int i=0;i<=st;i++)
    39             {
    40                 if(sum[i]>1) {sum[i]-=2;sum[i+1]++;}
    41                 if(sum[i]) sum[i+1]++;
    42             }
    43             while(st&&!sum[st]) st--;
    44             for(int i=st;i>=0;i--) printf("%d",sum[i]);
    45         }
    46         puts("");
    47     }
    48     return 0;
    49 }
    Aguin

    补BC。

    HDU 5501 The Highest Mark

    背包好想。贪心的部分赛时没想到。Hack时看别人代码也没想明白QAQ。

    其实考虑物品选定后如何排序就好了。题解很清楚了。

     1 #include <iostream>
     2 #include <cstdio>
     3 #include <cstring>
     4 #include <algorithm>
     5 using namespace std;
     6 int dp[3010];
     7 
     8 struct node
     9 {
    10     int A,B,C;
    11 }p[1010];
    12 
    13 bool cmp(node a,node b)
    14 {
    15     return a.C*b.B<b.C*a.B;
    16 }
    17 
    18 int main(void)
    19 {
    20     int T; cin>>T;
    21     while(T--)
    22     {
    23         int n,t;
    24         scanf("%d%d",&n,&t);
    25         for(int i=0;i<n;i++) scanf("%d%d%d",&p[i].A,&p[i].B,&p[i].C);
    26         sort(p,p+n,cmp);
    27         memset(dp,0,sizeof(dp));
    28         for(int i=0;i<n;i++)
    29             for(int V=t;V>=p[i].C;V--)
    30                 dp[V]=max(dp[V],dp[V-p[i].C]+p[i].A-V*p[i].B);
    31         int ans=0;
    32         for(int i=0;i<=t;i++) ans=max(ans,dp[i]);
    33         printf("%d
    ",ans);
    34     }
    35     return 0;
    36 }
    Aguin
  • 相关阅读:
    Java基础知识总结(绝对经典)
    mybatis注解详解
    div行内样式style常用属性
    php中json_decode()和json_encode()的使用方法
    java调用javascript :js引擎rhino
    DeleteDC() 与 ReleaseDC() 的区别 [转]
    non-manifold Mesh(非流形网格)
    C++静态成员函数小结 [转]
    C++ 类的静态成员详细讲解[转]
    CString 转 char*; wstring 转 string
  • 原文地址:https://www.cnblogs.com/Aguin/p/4854239.html
Copyright © 2011-2022 走看看