HDU 5183
呃。。其实挺水的一题,不说了。。伤心。。
这题应该是要分开奇偶性的,因为如果不分开,当a0+...+ai=0,a(i+1)+....+aj=K时,求出来会出错。
维护两种前缀和,
sum=a0-a1+a2......ai
sum=-a0+a1-a2.....ai
维护两个HASH,第一种前缀和当i为奇数时加入,第二种当i为偶数时加入,查找时查询sum-K,-SUM-K
#include <cstdio> #include <iostream> #include <cstring> #include <cctype> #include <algorithm> #define LL __int64 using namespace std; const LL N=1000050; int a[N]; LL K; struct Hash{ int tot; int nxt[N]; int head[N]; LL sum[N]; void init(){ tot=0; memset(head,-1,sizeof(head)); } bool findx(LL num){ LL mod=((num%N)+N)%N; bool flag=false; for(int i=head[mod];i!=-1;i=nxt[i]){ if(sum[i]==num){ flag=true; break; } } return flag; } void addin(LL num){ if(findx(num)) return ; LL mod=((num%N)+N)%N; sum[tot]=num; nxt[tot]=head[mod]; head[mod]=tot++; } }H0,H1; void in(int &x) { char ch = getchar(); int tag = 1; x = 0; while((ch < '0'|| ch > '9')) { if(ch == '-') tag = -1; ch = getchar(); } while(ch >= '0' && ch <= '9') { x = x*10 + ch - 48; ch = getchar(); } x*=tag; } int main(){ int T,n,t=0; LL tmp; scanf("%d",&T); while(T--){ H0.init(); H1.init(); scanf("%d%I64d",&n,&K); // getchar(); LL pre=0; bool flag; // H0.addin(0); H1.addin(0); for(int i = 0; i < n; ++i) { in(a[i]); } for(int i=0;i<n;i++){ flag=false; if(i%2==0) pre=pre+a[i]; else pre=pre-a[i]; if(H1.findx(pre-K)){ flag= true; break; } if(H0.findx(-pre-K)) { flag=true; break; } if(i%2){ H1.addin(pre); } else H0.addin(-pre); } if(flag){ printf("Case #%d: Yes.\n",++t); } else printf("Case #%d: No.\n",++t); } return 0; }