codeforces 1042 c
思路简单,但代码较复杂的贪心
分类讨论:
- 有0
- 负数有奇数个:将最大的负数和0全部乘到一起,最后删掉0
- 负数有偶数个:将0全部乘到一起,最后删掉0
- 没有0
- 负数有奇数个:将最大绝对值最小的负数删掉
- 负数有偶数个:不删
#include <iostream> #include<string.h> #include<cstdio> #include<algorithm> using namespace std; typedef long long ll; int main() { ll n,i,j,k,t,maxx=-0x3f3f3f3f,t1,a[200010]={0},fu=0,ling=0,c[200010],d[200010]; scanf("%lld",&n); for(i=0; i<=n-1; i++) { scanf("%lld",&a[i]); if(a[i]<0) { fu++; if(a[i]>maxx) { maxx=a[i]; k=i; } } if(a[i]==0) ling++; } if(ling!=0) { if(fu%2==0) { memset(c,0,sizeof(c)); memset(d,0,sizeof(d)); t=0; t1=0; int ge=0; for(i=0; i<=n-1; i++) { if(a[i]==0) c[t++]=i+1; if(a[i]!=0) d[t1++]=i+1; } for(i=0; i<=t-2; i++) { printf("1 %lld %lld ",c[i],c[i+1]); ge++; } if(ge==n-1) return 0; printf("2 %lld ",c[t-1]); for(i=0; i<=t1-2; i++) { printf("1 %lld %lld ",d[i],d[i+1]); } } else { memset(c,0,sizeof(c)); memset(d,0,sizeof(d)); t=0; t1=0; int ge=0; for(i=0; i<=n-1; i++) { if(a[i]==0||i==k) c[t++]=i+1; else d[t1++]=i+1; } for(i=0; i<=t-2; i++) { printf("1 %lld %lld ",c[i],c[i+1]); ge++; } if(ge==n-1) return 0; printf("2 %lld ",c[t-1]); for(i=0; i<=t1-2; i++) { printf("1 %lld %lld ",d[i],d[i+1]); } } } else { if(fu%2!=0) { memset(c,0,sizeof(c)); memset(d,0,sizeof(d)); t=0; t1=0; int ge=0; for(i=0; i<=n-1; i++) { if(i==k) c[t++]=i+1; else d[t1++]=i+1; } for(i=0; i<=t-2; i++) { printf("1 %lld %lld ",c[i],c[i+1]); ge++; } if(ge==n-1) return 0; printf("2 %lld ",c[t-1]); for(i=0; i<=t1-2; i++) { printf("1 %lld %lld ",d[i],d[i+1]); } } else { memset(c,0,sizeof(c)); memset(d,0,sizeof(d)); t=0; t1=0; for(i=0; i<=n-1; i++) { if(a[i]!=0) d[t1++]=i+1; } for(i=0; i<=t1-2; i++) { printf("1 %lld %lld ",d[i],d[i+1]); } } } }