【UOJ 209】【UER #6】票数统计
2016-07-08 12:09
375 查看
Description
原题链接妹滋滋是一个善于编程的女孩子。
但是某一天,她一不小心把 UOJ 后台的票数统计程序写错了。
本来嘛在这种根本没有什么用的功能上出了 bug 也没有什么大关系,但是又有某一天,UOJ 突然就开始搞全民公投了。
这可怎么办呢?如果这个消息让别人知道的话自己肯定会被查表,更不要说让所有用户重新来投一次票了。
作为一个要强的女孩子,妹滋滋决定自力更生。
通过一些奥妙重重的方式,妹滋滋知道了一些关于这次全民公投的信息。
这次全民公投一共有 n 位用户排队参加,编号为 1 到 n。每一位用户要么投了通过,要么投了不通过。
有 mm 个二元组 (xi,yi),每个二元组给出这样一个信息: “前 xi位用户中,恰好 yi 位投了通过” 和 “后 yi 位用户中,恰好有 xi 位投了通过” 这两句话中,至少有一句是成立的。
作为分析的第一步,她想要知道有多少种投票情况是满足她所得到的信息的。当然,可能所有投票情况都不满足条件。
Solution
很显然,当x>y时就是第二种情况,而对于所有的x=y的情况,只有最大x是有用的,
所有我们枚举所有投票的人,这样所有的对后缀的限制就变成了前缀,
于是可以愉快的用C公式搞,
对于x=y,只要符合前缀的情况+符合后缀的情况-两个多符合的情况即可,
复杂度:O(n2)
Code
#include<cstdio> #include<cstdlib> #include<cstring> #include<algorithm> #define fo(i,a,b) for(int i=a;i<=b;i++) #define fod(i,a,b) for(int i=a;i>=b;i--) using namespace std; typedef long long LL; const int N=5555,mxlongint=2147483640,mo=998244353; int read(int &n) { char ch=' ';int q=0,w=1; for(;(ch!='-')&&((ch<'0')||(ch>'9'));ch=getchar()); if(ch=='-')w=-1,ch=getchar(); for(;ch>='0' && ch<='9';ch=getchar())q=q*10+ch-48;n=q*w;return n; } int n,m,m1,c; LL ans; struct qqww {int x,y,s;}a ; LL C ; bool PX(qqww a,qqww b) { int q=a.x,w=b.x; if(a.s==1||a.s==2)q=n-q+1; if(b.s==1||b.s==2)w=n-w+1; return (q<w)||((q==w)&&(a.s>b.s)); } LL ss(int m1) { int q,w,e=m; LL ans,ANS=0; int l=0,l1=0,c1,c2; fo(i,1,m)if(a[i].s!=2) { if(a[i].s==1) { q=n-a[i].x,w=m1-a[i].y; if(a[i].y+a[i].x-1<m1){l1=n;break;} } else { q=a[i].x,w=a[i].y; if(a[i].s==0){l1=n;break;} } if(a[i].s==-1){e=i;break;} if(w<0||q<0)return 0; if(!C[q-l][w-l1])return 0; l=q,l1=w; } if(l1<=c&&l1+q-l>=c) { c1=e; l=l1=a[e].x;ans=1; fo(i,e+1,m)if(a[i].s!=2) { if(a[i].s==1)q=n-a[i].x,w=m1-a[i].y;else q=a[i].x,w=a[i].y; if(w-l1<0||q<0)ans=0; ans=(ans*C[q-l][w-l1])%mo; if(!ans)break; l=q,l1=w; } if(n-l<0||m1-l1<0)ans=0;else ans=(ans*C[n-l][m1-l1])%mo; ANS=ans; if(!ans)c1=0; }else c1=0; if(!c)return ANS; l=n+1,l1=e=0; fod(i,m,1)if(a[i].s!=-1) { if(a[i].s==0) { q=a[i].x,w=m1-a[i].y; if(a[i].y+n-a[i].x<m1){l1=n;break;} } else { q=n-a[i].x,w=a[i].y; if(a[i].s==1){l1=n;break;} } if(a[i].s==2){e=i;break;} if(w-l1<0||q<0)return 0; if(!C[l-q][w-l1])return 0; l=q,l1=w; } if(l1<=c&&l1+l-q>=c) { l1=a[e].x,l=n-a[e].x;ans=1; c2=e; fod(i,e-1,1)if(a[i].s!=-1) { if(!a[i].s)q=a[i].x,w=m1-a[i].y;else q=n-a[i].x,w=a[i].y; if(w-l1<0||q<0)ans=0; ans=(ans*C[l-q][w-l1])%mo; if(!ans)break; l=q,l1=w; } if(n-l<0||m1-l1<0)ans=0;else ans=(ans*C[l][m1-l1])%mo; ANS+=ans; }else c2=0; if(ans&&c1&&c2) if(c*2>=n)ANS-=(m1==n); else if(m1>=c*2) { l=l1=a[e].x;ans=1; fo(i,c1+1,c2-1) { if(a[i].s==1)q=n-a[i].x,w=m1-a[i].y;else q=a[i].x,w=a[i].y; if(w-l1<0||q<0)ans=0; ans=(ans*C[q-l][w-l1])%mo; if(!ans)break; l=q,l1=w; } ans=(ans*C[n-c-l][m1-l1-c])%mo; ANS-=ans; } return ANS%mo; } int main() { int q,w,_,mx; fo(i,0,N-550) { C[i][0]=1; fo(j,1,i)C[i][j]=(C[i-1][j]+C[i-1][j-1])%mo; } read(_); while(_--) { read(n),read(m); m1=c=0;mx=1; ans=0; fo(i,1,m) { q=read(a[++m1].x),w=read(a[m1].y); if(q>n||w>n)ans=-1; if(q>w)a[m1].s=0,mx=max(mx,a[m1].y); else if(q<w)a[m1].s=1,swap(a[m1].x,a[m1].y),mx=max(mx,a[m1].y); else { if(c<a[m1].x)c=a[m1].x; m1--; } } m=m1; a[++m].x=a[m].y=c,a[m].s=-1; if(c)a[++m].x=a[m].y=c,a[m].s=2; sort(a+1,a+1+m,PX); fo(i,2,m) if(a[i].x==a[i-1].x&&a[i].s==a[i-1].s&&a[i].y!=a[i-1].y)ans=-1; if(c==n&&m>2)ans=-1; if(ans==-1){printf("0\n");continue;} fo(i,mx,n)ans=(ans+ss(i))%mo; printf("%d\n",(ans+mo)%mo); } return 0; }
相关文章推荐
- 找不到符号: 变量 BuildConfig
- UITextField文本字段控件的位置
- WRONGTYPE Operation against a key holding the wrong kind of value
- UITextField占位文字颜色-attributedPlaceholder
- Java并发编程与技术内幕:ArrayBlockingQueue、LinkedBlockingQueue及SynchronousQueue源码解析
- Process 'command '/Users/wcc/Android/sdk/build-tools/23.0.0/aidl'' finished with non-zero exit valu
- CUICatalog: Invalid asset name supplied:
- Android Bluetooth Low Energy官方文档翻译
- abap 弹出对话框函数POPUP_GET_VALUES的使用方法
- 如何监控项目里所有UI线程的操作(实战,BlockCanary)?
- UITextView的placehoder背景文字实现带并限制文字字数
- UICollectionReusableView 使用时的一些问题
- @value注解使用的简单介绍 ---谷营中西
- 数据类型变换uint8_t uint16_t等等
- Android 在子线程中更新UI的方式,使用handler
- Warning:The remote SSH server rejected X11 forwarding request.
- UICollectionViewLayout
- Errors running builder 'Validation' on project 'jumi_3.0'
- 点击tabBarItem跳转到其他界面 返回后还是之前所选item (跳转注册)
- php中生成标准uuid(guid)的方法