摘要: 题意:在一个无向连通图上,求任意删除一个点,余下连通块的个数。对于一个非割顶的点,删除之后,原图仍连通,即余下连通块个数为1;对于割顶,余下连通块个数>=2。由于是用dfs查找双连通分量,树形结构是向下搜素,所以在dfs过程中不便于统计割顶所分连通分量的个数。换一个角度,通过在vectorbcc中保存各个双连通分量的点,统计各个点出现的次数即可。(除割顶外,每个点只可能出现一次) 1 #include 2 #include 3 #include 4 #include 5 #include 6 using namespace std; 7 8 const int MAXN= 1... 阅读全文
posted @ 2013-08-07 13:12 Thousand Sunny 阅读(278) 评论(0) 推荐(0) 编辑
摘要: 这道题在LA是挂掉了,不过还好,zoj上也有这道题。题意:好大一颗树,询问父子关系。。考虑最坏的情况,30w层,2000w个点,询问100w次,貌似连dfs一遍都会TLE。安心啦,这肯定是一道正常人能做的题目。不过是需要几个小技巧。1、2000w个点不一定都要保存下来,事实上,虽然题目给了256M的空间,只要开了两个这么大的数组,MLE是跑不了的,所以只保存30w个父节点。2、如果这30w个父节点构成一条链,dfs的栈肯定爆。所以需要用栈模拟dfs。这里用的是stack,当然手写栈会更快。注意:1、时间戳的使用。 2、本题中顺序对节点标号,使得所有>=n的节点都是叶子节点,同时能够二分也 阅读全文
posted @ 2013-08-07 10:32 Thousand Sunny 阅读(524) 评论(0) 推荐(0) 编辑
摘要: 以“爪”形为单元,问所给出的无向图中能否被完全分割成一个个单元。分析图的性质,由于已知每个点的度是3,所以“爪”之间是相互交错的,即把一个“爪”分为中心点和边缘点,中心点被完全占据,而边缘点被三个“爪”瓜分。分析到这里,用二分图的性质就可以解决了。 1 #include 2 #include 3 #include 4 #include 5 using namespace std; 6 7 const int MAXN=333; 8 9 int color[MAXN];10 vectorG[MAXN];11 queueq;12 13 bool Bjudge()14 {15 memse... 阅读全文
posted @ 2013-08-06 22:32 Thousand Sunny 阅读(393) 评论(0) 推荐(0) 编辑
摘要: 2-sat问题,一种在两种可能性中选择必然关系的问题。推荐两篇论文,也是学2-sat公认比较好的材料。前者较好理解,后者需耐心看。http://www.google.com.hk/url?sa=t&rct=j&q=2-sat&source=web&cd=6&ved=0CEUQFjAF&url=http%3a%2f%2fbbs%2ebyr%2ecn%2fwForum%2fboardcon%2ephp%3fbid%3d212%26id%3d15887%26ftype%3d3%26ap%3d369&ei=30wAUsrlDYLHkwXam4Go 阅读全文
posted @ 2013-08-06 09:45 Thousand Sunny 阅读(283) 评论(0) 推荐(0) 编辑
摘要: 求最大团。和等价性证明有类似之处,只不过这个不是求互推,而是只要a->b,或b->a即可。同样的,容易想到先缩点,得到DAG,每个节点上保存SCC的点数,相信任意一条由根节点(入度为零)出发的路径中权值和最大的即为所求,dp即可解决。 1 #include 2 #include 3 #include 4 #include 5 using namespace std; 6 7 const int MAXN=1111; 8 const int MAXM=55555; 9 10 struct Edge{ 11 int v,next; 12 }edge[MAXM]; 13... 阅读全文
posted @ 2013-08-06 09:04 Thousand Sunny 阅读(274) 评论(0) 推荐(0) 编辑
摘要: 等价性问题,给出的样例为 a->b的形式,问要实现全部等价(即任意两个可以互相推出),至少要加多少个形如 a->b的条件。容易想到用强连通缩点,把已经实现等价的子图缩掉,最后剩余DAG。要推出一个方案,YY后取“出度为零”和“入度为零”的点数的较大值。理由:假定出度为零的点数较多,即是我们通常意义上的树的形式(当然,DAG是图,这里只是类比)。根可以推出其所有子孙,事实上任意一个点都可以推出其子孙,那么只要让该节点推出树根,就可以推出整棵树上所有的节点了。那么多棵树为什么不是相乘呢?,借题目中的范例,a->b,b->c,c->a,形成一个循环即可。本质:给定一个有 阅读全文
posted @ 2013-08-06 08:45 Thousand Sunny 阅读(254) 评论(0) 推荐(0) 编辑
摘要: 题目真心分析不出来。看了白书才明白,不过有点绕脑。容易想到,把题目给的不相邻的关系,利用矩阵,反过来建图。既然是全部可行的关系,那么就应该能画出含奇数个点的环。求环即是求双连通分量:找出所有的双连通分量,只要分量中的点数是奇数,则排除“must be expelled”的可能性。判环上的点数用二分图,这个我都想了半天= =,如果是奇数个点,明摆着多出来的一个点放到哪个集合都会与集合内的点连边(这个找三个点自己画画试试就明白了)。0、1染色,本人喜欢用bfs,递归什么的其实都可以。我自己用缩点做的,果断wa到吐。举个例子:五个点,{1,2,3}{3,4,5},这样3就是一个割顶了,缩点的话是在遍 阅读全文
posted @ 2013-08-02 23:50 Thousand Sunny 阅读(437) 评论(0) 推荐(0) 编辑
摘要: 简单题的伪装太犀利了,我完全被蒙住了,结果还从左上角模拟一遍。。。事实上,右下角是0,则Bob赢;否则Alice赢。这种规律怎么就是想不到呢,YY能力不够啊= = 1 #include 2 #include 3 char str[101]; 4 int main() 5 { 6 int T,n,m; 7 scanf("%d",&T); 8 while(T--) 9 {10 scanf("%d%d",&n,&m);11 getchar();12 for(int i=0;i<n;i++)13 g... 阅读全文
posted @ 2013-08-02 22:27 Thousand Sunny 阅读(153) 评论(0) 推荐(0) 编辑
摘要: 这个我只能说出题人太和谐了,不仅“hehe”,还拿斐波那契额数列逗我们。。。 1 #include 2 #include 3 4 int f[5050]; 5 char str[10100]; 6 7 int main() 8 { 9 int T;10 scanf("%d",&T);11 f[0]=f[1]=1;12 for(int i=2;i<5050;i++)13 f[i]=(f[i-1]+f[i-2])%10007;14 for(int k=1;k<=T;k++)15 {16 scanf("%s",str... 阅读全文
posted @ 2013-08-02 22:22 Thousand Sunny 阅读(115) 评论(0) 推荐(0) 编辑
摘要: 考强连通缩点,算模板题吧,比赛的时候又想多了,大概是不自信吧,才开始认真搞图论,把题目想复杂了。题意就是给你任意图,保证是simple directed graph,问最多加多少条边能使图仍然是simple directed graph,即 无重边且整个图非强连通。容易想到把所有的点分成两个集合,只要在同一个方向上把所有边都连上就很理想。那么点该如何分配呢?差值尽可能的大,因为总的边数不单单是两集合之间的边,还要算上集合内部全部的边,注意集合内部是在保证不出现重边的条件下的所有的边。令总点数为n,一个集合的点数为k,则两个集合内的边数分别为 k*(k-1),(n-k)*(n-k-1)条,而两集 阅读全文
posted @ 2013-08-02 22:19 Thousand Sunny 阅读(205) 评论(0) 推荐(0) 编辑