﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>C++博客-Mato is No.1-随笔分类-动态规划</title><link>http://www.cppblog.com/MatoNo1/category/17262.html</link><description>Mato是一只超级大沙茶……但他一直以来都想成为各项比赛都No.1的神犇……</description><language>zh-cn</language><lastBuildDate>Thu, 07 Mar 2013 20:58:12 GMT</lastBuildDate><pubDate>Thu, 07 Mar 2013 20:58:12 GMT</pubDate><ttl>60</ttl><item><title>【AHOI2013复仇】二维DP优化的几道题总结</title><link>http://www.cppblog.com/MatoNo1/archive/2013/03/03/198185.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Sun, 03 Mar 2013 07:25:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2013/03/03/198185.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/198185.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2013/03/03/198185.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/198185.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/198185.html</trackback:ping><description><![CDATA[<div>【1】<a title="BZOJ1713" href="http://www.lydsy.com/JudgeOnline/problem.php?id=1713">BZOJ1713<br /></a>F[i][j]=max{F[i1][j1] - (sA[i-1]-sA[i1])<sup>2</sup> - (sB[j-1]-sB[j1])<sup>2</sup>} + A[i]*B[j], 0&lt;=i1&lt;i, 0&lt;=j1&lt;j<br />对这个式子进行化简：<br />F[i][j]=max{F[i1][j1] - sA[i1]<sup>2</sup> + 2*sA[i-1]*sA[i1] - sB[j1]<sup>2</sup> + 2*sB[j-1]*sB[j1]}+A[i]*B[j]-sA[i-1]<sup>2</sup>-sB[j-1]<sup>2</sup><br />对于一维的情况，很容易处理&#8212;&#8212;中间就是一条直线，然而这是二维的，对于这种2D/2D的DP方程，要优化到O(N<sup>2</sup>)级别，需要两步。<br />注意到决策式中除了F[i1][j1]外，其它部分都要么只与i1有关，要么只与j1有关。因此，可以把阶段i的各个状态作为一个整体，在之前得出的各个F[i][j]中，对于相同的j，找到对于目前的i，最优的那个决策&#8212;&#8212;注意，对于相同的j1，里面所有与j1有关的东西都可以先不考虑了，只考虑(F[i1][j1] - sA[i1]<sup>2</sup> + 2*sA[i-1]*sA[i1])对于目前i的最优决策。这一步可以在这些直线形成的上凸壳中找到，且满足决策单调性，可以用一个栈处理（斜率优化）。然后，将这些最优决策以j为自变量再组成一些直线，用栈维护它们的上凸壳，对于每个j，找到最优值即可。<br />注意事项：在栈中删除直线的时候，如果之前的最优决策是这个被删掉的直线，则要将最优决策先置为不存在，然后再插入新直线后设为新直线。另外，要特别注意平行的情况。<br /><br />【2】LCIS<br />经典问题，利用上面的分步优化思想，很容易用线段树得到一个O(N<sup>2</sup>logN)的做法。<br /><br />【3】<a title="[SCOI2010]股票交易 " href="http://www.lydsy.com/JudgeOnline/problem.php?id=1855">[SCOI2010]股票交易</a><br />F[i][j]=max{F[i-1][j], max{F[i-W-1][j-a]-A*a, F[i-W-1][j+b]+b*B}}, j&lt;=maxP, 1&lt;=a&lt;=maxA, 1&lt;=b&lt;=maxB<br />注意对于相同的j，计算方法是一样的，且是一条直线（由于有范围所以其实是线段）。<br />所以，计算阶段i时，可以将(i-W-1)阶段所有的决策当成线段插入，这些线段的斜率都相等，因此比较好维护，只需要判断边界即可。<br /><br />注意，NOI2011的show虽然也符合对于相同的j计算方法一样，但它就不能优化，因为它的决策是不连续且无规律的，没有任何几何性质。因此，它只能用O(N<sup>3</sup>)的算法计算出所有状态。<br /><a title="[SCOI2010]股票交易 " href="http://www.lydsy.com/JudgeOnline/problem.php?id=1855"> </a></div><img src ="http://www.cppblog.com/MatoNo1/aggbug/198185.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2013-03-03 15:25 <a href="http://www.cppblog.com/MatoNo1/archive/2013/03/03/198185.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>【AHOI2013复仇】动态凸包</title><link>http://www.cppblog.com/MatoNo1/archive/2013/02/28/198024.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Thu, 28 Feb 2013 10:29:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2013/02/28/198024.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/198024.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2013/02/28/198024.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/198024.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/198024.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: 原题地址写了几天终于写出来了&#8230;&#8230;（显然，我太弱了，请各位神犇不要鄙视）在有加点的情况下，动态地维护凸包，有以下两种方法：&lt;1&gt;维护上、下凸壳（本沙茶采用的方法）：凸包可以拆成上、下凸壳，对它们分别维护。两个凸壳均按照下面定义的&lt;关系（即先x增、再y增）排序，注意，两个凸壳的两端是相同的，均为整个凸包的最小点与最大点，除两端外，它们没有公共定点。以上凸壳为例...&nbsp;&nbsp;<a href='http://www.cppblog.com/MatoNo1/archive/2013/02/28/198024.html'>阅读全文</a><img src ="http://www.cppblog.com/MatoNo1/aggbug/198024.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2013-02-28 18:29 <a href="http://www.cppblog.com/MatoNo1/archive/2013/02/28/198024.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>【AHOI2013复仇】SCOI2008 着色方案</title><link>http://www.cppblog.com/MatoNo1/archive/2012/10/24/193778.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Wed, 24 Oct 2012 06:59:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2012/10/24/193778.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/193778.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2012/10/24/193778.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/193778.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/193778.html</trackback:ping><description><![CDATA[<a title="原题地址" href="http://www.lydsy.com/JudgeOnline/problem.php?id=1079">原题地址</a><br />首先，看这么小的范围就知道，数学方法肯定搞不了&#8230;&#8230;又想不到其它模型&#8230;&#8230;只能用状压硬搞了囧&#8230;&#8230;<br />问题是，5^15稳T，如果能倒过来，15^5，就不会T了。<br />可以发现，C值相同的颜色本质上是一样的&#8230;&#8230;因此，只需要保存目前C值为1、2、3、4、5的颜色各有多少种就行了囧&#8230;&#8230;（当然在过程中还会出现C值为0的，即用完的颜色，不过0、1、2、3、4、5的和是颜色总数，而且从下面可以看出，C值为0的确实&#8220;木有用&#8221;）；<br />设F[s1][s2][s3][s4][s5][v]为涂完前若干个木块（这个个数可以通过s1~s5算出，不过我们并不需要它囧&#8230;&#8230;）后，C值为1~5的颜色各有s1～s5种，且这若干个中的<strong><span style="color: red;">最后一个涂的颜色还剩的C值</span></strong>为v（显然0&lt;=v&lt;=4）。<br />边界：F[S[1]][S[2]][S[3]][S[4]][S[5]][0]=1，其余为0（S[i]为一开始C值为i的颜色种数）。<br />计算F时，前推后（注意顺序，是按照S[5]逆序最先，再依次是S[4]～S[1]，都是逆序，v可任意定序），枚举下一个木块的颜色是现在还剩多少的，如果它与目前的这个（最后一个）剩的相同，则要减1，否则不减。具体的方程见代码。<br />注意细节：枚举F的s1~s5下标时，都要N（颜色总数）开始枚举，因为过程中某些s值会增加；<br /><br />本题的启示就是，在设计状压DP的时候，如果正着来不行，可以反着来，或许就能设计出符合要求的解法。<br /><br />代码：<br /><div style="background-color: #eeeeee; font-size: 13px; border: 1px solid #cccccc; padding: 4px 5px 4px 4px; width: 98%;"><span style="color: #000000;">#include&nbsp;</span><span style="color: #000000;">&lt;</span><span style="color: #000000;">iostream</span><span style="color: #000000;">&gt;</span><span style="color: #000000;"><br />#include&nbsp;</span><span style="color: #000000;">&lt;</span><span style="color: #000000;">stdio.h</span><span style="color: #000000;">&gt;</span><span style="color: #000000;"><br />#include&nbsp;</span><span style="color: #000000;">&lt;</span><span style="color: #000000;">stdlib.h</span><span style="color: #000000;">&gt;</span><span style="color: #000000;"><br />#include&nbsp;</span><span style="color: #000000;">&lt;</span><span style="color: #0000ff;">string</span><span style="color: #000000;">.h</span><span style="color: #000000;">&gt;</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">using</span><span style="color: #000000;">&nbsp;</span><span style="color: #0000ff;">namespace</span><span style="color: #000000;">&nbsp;std;<br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;re(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=0;&nbsp;i&lt;n;&nbsp;i++)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;re1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=1;&nbsp;i&lt;=n;&nbsp;i++)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;re2(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;r;&nbsp;i++)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;re3(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;=r;&nbsp;i++)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;rre(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n-1;&nbsp;i&gt;=0;&nbsp;i--)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;rre1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n;&nbsp;i&gt;0;&nbsp;i--)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;rre2(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r-1;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;rre3(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">#define</span><span style="color: #000000;">&nbsp;ll&nbsp;long&nbsp;long</span><span style="color: #000000;"><br /></span><span style="color: #0000ff;">const</span><span style="color: #000000;">&nbsp;</span><span style="color: #0000ff;">int</span><span style="color: #000000;">&nbsp;n&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">5</span><span style="color: #000000;">,&nbsp;MAXM&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">16</span><span style="color: #000000;">,&nbsp;MOD&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1000000007</span><span style="color: #000000;">;<br /></span><span style="color: #0000ff;">int</span><span style="color: #000000;">&nbsp;m,&nbsp;S[n&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">];<br />ll&nbsp;F[MAXM][MAXM][MAXM][MAXM][MAXM][n],&nbsp;res;<br /></span><span style="color: #0000ff;">void</span><span style="color: #000000;">&nbsp;init()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;scanf(</span><span style="color: #000000;">"</span><span style="color: #000000;">%d</span><span style="color: #000000;">"</span><span style="color: #000000;">,&nbsp;</span><span style="color: #000000;">&amp;</span><span style="color: #000000;">m);&nbsp;</span><span style="color: #0000ff;">int</span><span style="color: #000000;">&nbsp;x;<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;m)&nbsp;{scanf(</span><span style="color: #000000;">"</span><span style="color: #000000;">%d</span><span style="color: #000000;">"</span><span style="color: #000000;">,&nbsp;</span><span style="color: #000000;">&amp;</span><span style="color: #000000;">x);&nbsp;S[x]</span><span style="color: #000000;">++</span><span style="color: #000000;">;}<br />}<br /></span><span style="color: #0000ff;">void</span><span style="color: #000000;">&nbsp;solve()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;F[S[</span><span style="color: #000000;">1</span><span style="color: #000000;">]][S[</span><span style="color: #000000;">2</span><span style="color: #000000;">]][S[</span><span style="color: #000000;">3</span><span style="color: #000000;">]][S[</span><span style="color: #000000;">4</span><span style="color: #000000;">]][S[</span><span style="color: #000000;">5</span><span style="color: #000000;">]][</span><span style="color: #000000;">0</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">;&nbsp;</span><span style="color: #0000ff;">int</span><span style="color: #000000;">&nbsp;tmp;<br />&nbsp;&nbsp;&nbsp;&nbsp;rre3(i5,&nbsp;m,&nbsp;</span><span style="color: #000000;">0</span><span style="color: #000000;">)&nbsp;rre3(i4,&nbsp;m,&nbsp;</span><span style="color: #000000;">0</span><span style="color: #000000;">)&nbsp;rre3(i3,&nbsp;m,&nbsp;</span><span style="color: #000000;">0</span><span style="color: #000000;">)&nbsp;rre3(i2,&nbsp;m,&nbsp;</span><span style="color: #000000;">0</span><span style="color: #000000;">)&nbsp;rre3(i1,&nbsp;m,&nbsp;</span><span style="color: #000000;">0</span><span style="color: #000000;">)&nbsp;re(v,&nbsp;n)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(F[i1][i2][i3][i4][i5][v])&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(i1)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(v&nbsp;</span><span style="color: #000000;">==</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">)&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i1&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">;&nbsp;</span><span style="color: #0000ff;">else</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i1;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(tmp)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i2][i3][i4][i5][</span><span style="color: #000000;">0</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">+=</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">*</span><span style="color: #000000;">&nbsp;F[i1][i2][i3][i4][i5][v];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i2][i3][i4][i5][</span><span style="color: #000000;">0</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">%=</span><span style="color: #000000;">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(i2)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(v&nbsp;</span><span style="color: #000000;">==</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">2</span><span style="color: #000000;">)&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i2&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">;&nbsp;</span><span style="color: #0000ff;">else</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i2;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(tmp)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i2&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i3][i4][i5][</span><span style="color: #000000;">1</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">+=</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">*</span><span style="color: #000000;">&nbsp;F[i1][i2][i3][i4][i5][v];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i2&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i3][i4][i5][</span><span style="color: #000000;">1</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">%=</span><span style="color: #000000;">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(i3)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(v&nbsp;</span><span style="color: #000000;">==</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">3</span><span style="color: #000000;">)&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i3&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">;&nbsp;</span><span style="color: #0000ff;">else</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i3;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(tmp)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1][i2&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i3&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i4][i5][</span><span style="color: #000000;">2</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">+=</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">*</span><span style="color: #000000;">&nbsp;F[i1][i2][i3][i4][i5][v];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1][i2&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i3&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i4][i5][</span><span style="color: #000000;">2</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">%=</span><span style="color: #000000;">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(i4)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(v&nbsp;</span><span style="color: #000000;">==</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">4</span><span style="color: #000000;">)&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i4&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">;&nbsp;</span><span style="color: #0000ff;">else</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;i4;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(tmp)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1][i2][i3&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i4&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i5][</span><span style="color: #000000;">3</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">+=</span><span style="color: #000000;">&nbsp;tmp&nbsp;</span><span style="color: #000000;">*</span><span style="color: #000000;">&nbsp;F[i1][i2][i3][i4][i5][v];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1][i2][i3&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i4&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i5][</span><span style="color: #000000;">3</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">%=</span><span style="color: #000000;">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(i5)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1][i2][i3][i4&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i5&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][</span><span style="color: #000000;">4</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">+=</span><span style="color: #000000;">&nbsp;i5&nbsp;</span><span style="color: #000000;">*</span><span style="color: #000000;">&nbsp;F[i1][i2][i3][i4][i5][v];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i1][i2][i3][i4&nbsp;</span><span style="color: #000000;">+</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][i5&nbsp;</span><span style="color: #000000;">-</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">1</span><span style="color: #000000;">][</span><span style="color: #000000;">4</span><span style="color: #000000;">]&nbsp;</span><span style="color: #000000;">%=</span><span style="color: #000000;">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;res&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;F[</span><span style="color: #000000;">0</span><span style="color: #000000;">][</span><span style="color: #000000;">0</span><span style="color: #000000;">][</span><span style="color: #000000;">0</span><span style="color: #000000;">][</span><span style="color: #000000;">0</span><span style="color: #000000;">][</span><span style="color: #000000;">0</span><span style="color: #000000;">][</span><span style="color: #000000;">0</span><span style="color: #000000;">];<br />}<br /></span><span style="color: #0000ff;">void</span><span style="color: #000000;">&nbsp;pri()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;cout&nbsp;</span><span style="color: #000000;">&lt;&lt;</span><span style="color: #000000;">&nbsp;res&nbsp;</span><span style="color: #000000;">&lt;&lt;</span><span style="color: #000000;">&nbsp;endl;<br />}<br /></span><span style="color: #0000ff;">int</span><span style="color: #000000;">&nbsp;main()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;init();<br />&nbsp;&nbsp;&nbsp;&nbsp;solve();<br />&nbsp;&nbsp;&nbsp;&nbsp;pri();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff;">return</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">0</span><span style="color: #000000;">;<br />}<br /></span></div><img src ="http://www.cppblog.com/MatoNo1/aggbug/193778.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2012-10-24 14:59 <a href="http://www.cppblog.com/MatoNo1/archive/2012/10/24/193778.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>【AHOI2013复仇】NOI2008 道路设计</title><link>http://www.cppblog.com/MatoNo1/archive/2012/09/22/191595.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Sat, 22 Sep 2012 08:21:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2012/09/22/191595.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/191595.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2012/09/22/191595.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/191595.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/191595.html</trackback:ping><description><![CDATA[<a title="原题地址" href="http://www.lydsy.com/JudgeOnline/problem.php?id=1063">原题地址</a><br />典型的二次递推/DP的题目。<br />首先，题目中的&#8220;不便利值&#8221;指的是某个点到根的路径上的木有被选定链覆盖的边的条数。<br /><br />第一问：设F[i][0..2]分别为当子树i中结点i的状态为不参与链（0）、作为某链端点（1）、作为某链中间点（2）时，子树i中的结点到i的最小不便利值。为了得到F，需要设立G[j][k(0..2)]表示结点i的前j棵子树中，有k棵的根结点与结点i接上的最小的最大不便利值。显然，不和i接上的，状态为0、1、2都行，但不便利值要加1，而和i接上的状态只能是0或1，不加1。<br /><br />问题是第二问。第二问的难点在于，<span style="color: red"><strong>当i取得最小不便利值时，i的每个子结点并非都取到最小不便利值</strong></span>。举个例子，结点i的最小不便利值为3，它的某个子结点j的最小不便利值为2，则当j与i接上时，子树j的内部既可以取不便利值为2的解，也可以取不便利值为3的解。所以，为了解决第二问，需要求出结点i的最小不便利值为x的解的总数。<strong><span style="color: red">万幸的是，x的范围并不是太大，可以证明，x不会超过log</span><sub style="color: red">3</sub><span style="color: red">N（下取整），也就是当N=100000时x最大为10。</span></strong>因此，最后仍然不会T掉。<br /><br />这题的一个启示就是，在求类似于&#8220;最优解计数&#8221;的问题中，<span style="color: red"><strong>不要认为当后面的状态取得最优解时，前面的状态一定取得最优解。</strong></span>因此，不能只记录某状态取得最优解的个数，而要记录该状态取得每一个可行解时的个数。<br /><br />代码：
<div style="border-right: #cccccc 1px solid; padding-right: 5px; border-top: #cccccc 1px solid; padding-left: 4px; font-size: 13px; padding-bottom: 4px; border-left: #cccccc 1px solid; width: 98%; word-break: break-all; padding-top: 4px; border-bottom: #cccccc 1px solid; background-color: #eeeeee"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #000000">#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">iostream</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdio.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdlib.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #0000ff">string</span><span style="color: #000000">.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br /></span><span style="color: #0000ff">using</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">namespace</span><span style="color: #000000">&nbsp;std;<br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=0;&nbsp;i&lt;n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=1;&nbsp;i&lt;=n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re2(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;r;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re3(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;=r;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n-1;&nbsp;i&gt;=0;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n;&nbsp;i&gt;0;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre2(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r-1;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre3(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;ll&nbsp;long&nbsp;long</span><span style="color: #000000"><br /></span><span style="color: #0000ff">const</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;MAXN&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">100010</span><span style="color: #000000">,&nbsp;MAXW&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">11</span><span style="color: #000000">,&nbsp;INF&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">~</span><span style="color: #000000">0U</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">struct</span><span style="color: #000000">&nbsp;edge&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;a,&nbsp;b,&nbsp;pre,&nbsp;next;<br />}&nbsp;E0[MAXN&nbsp;</span><span style="color: #000000">*</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">3</span><span style="color: #000000">],&nbsp;E[MAXN&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">];<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;n,&nbsp;m0,&nbsp;m,&nbsp;Q[MAXN],&nbsp;F[MAXN][</span><span style="color: #000000">3</span><span style="color: #000000">],&nbsp;G[MAXN][</span><span style="color: #000000">3</span><span style="color: #000000">],&nbsp;res1&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />ll&nbsp;MOD,&nbsp;FS[MAXN][MAXW][</span><span style="color: #000000">3</span><span style="color: #000000">],&nbsp;S[MAXN][MAXW][</span><span style="color: #000000">3</span><span style="color: #000000">],&nbsp;res2&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">bool</span><span style="color: #000000">&nbsp;vst[MAXN];<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;init_d()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;n)&nbsp;E0[i].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E0[i].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[i].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[i].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;i;&nbsp;m0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;n;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;add_edge0(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;a,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;b)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;E0[m0].a&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E0[m0].b&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;b;&nbsp;E0[m0].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E0[a].pre;&nbsp;E0[m0].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E0[a].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m0;&nbsp;E0[E0[m0].pre].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m0</span><span style="color: #000000">++</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;E0[m0].a&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;b;&nbsp;E0[m0].b&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E0[m0].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E0[b].pre;&nbsp;E0[m0].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;b;&nbsp;E0[b].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m0;&nbsp;E0[E0[m0].pre].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m0</span><span style="color: #000000">++</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;add_edge(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;a,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;b)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;E[m].a&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E[m].b&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;b;&nbsp;E[m].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[a].pre;&nbsp;E[m].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E[a].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m;&nbsp;E[E[m].pre].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m</span><span style="color: #000000">++</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;init()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;_M;&nbsp;scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">n,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">_M);&nbsp;cin&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;MOD;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(_M&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;n&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;{res1&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;res2&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;}&nbsp;init_d();&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;a0,&nbsp;b0;<br />&nbsp;&nbsp;&nbsp;&nbsp;re2(i,&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">,&nbsp;n)&nbsp;{scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">a0,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">b0);&nbsp;add_edge0(</span><span style="color: #000000">--</span><span style="color: #000000">a0,&nbsp;</span><span style="color: #000000">--</span><span style="color: #000000">b0);}<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;prepare()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;n)&nbsp;vst[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;Q[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;vst[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x,&nbsp;y;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;front</span><span style="color: #000000">=</span><span style="color: #000000">0</span><span style="color: #000000">,&nbsp;rear</span><span style="color: #000000">=</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;front</span><span style="color: #000000">&lt;=</span><span style="color: #000000">rear;&nbsp;front</span><span style="color: #000000">++</span><span style="color: #000000">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;x&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;Q[front];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E0[x].next;&nbsp;p&nbsp;</span><span style="color: #000000">!=</span><span style="color: #000000">&nbsp;x;&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E0[p].next)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E0[p].b;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">!</span><span style="color: #000000">vst[y])&nbsp;{vst[y]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;Q[</span><span style="color: #000000">++</span><span style="color: #000000">rear]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;y;&nbsp;add_edge(x,&nbsp;y);}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;n)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">!</span><span style="color: #000000">vst[i])&nbsp;{res1&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;res2&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;}<br />}<br />inline&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;minv3(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;s1,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;s2,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;s3)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;s0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;s1&nbsp;</span><span style="color: #000000">&lt;=</span><span style="color: #000000">&nbsp;s2&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;s1&nbsp;:&nbsp;s2;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;s0&nbsp;</span><span style="color: #000000">&lt;=</span><span style="color: #000000">&nbsp;s3&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;s0&nbsp;:&nbsp;s3;<br />}<br />inline&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;minv2(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;s1,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;s2)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;s1&nbsp;</span><span style="color: #000000">&lt;=</span><span style="color: #000000">&nbsp;s2&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;s1&nbsp;:&nbsp;s2;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;solve()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x,&nbsp;y,&nbsp;len,&nbsp;v1,&nbsp;v2,&nbsp;v01,&nbsp;v02;&nbsp;ll&nbsp;sum;<br />&nbsp;&nbsp;&nbsp;&nbsp;rre(i,&nbsp;n)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;x&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;Q[i];&nbsp;len&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;G[</span><span style="color: #000000">0</span><span style="color: #000000">][</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;G[</span><span style="color: #000000">0</span><span style="color: #000000">][</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;G[</span><span style="color: #000000">0</span><span style="color: #000000">][</span><span style="color: #000000">2</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;INF;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E[x].next;&nbsp;p&nbsp;</span><span style="color: #000000">!=</span><span style="color: #000000">&nbsp;x;&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E[p].next)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[p].b;&nbsp;len</span><span style="color: #000000">++</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v1&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;minv3(F[y][</span><span style="color: #000000">0</span><span style="color: #000000">],&nbsp;F[y][</span><span style="color: #000000">1</span><span style="color: #000000">],&nbsp;F[y][</span><span style="color: #000000">2</span><span style="color: #000000">])&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;v2&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;minv2(F[y][</span><span style="color: #000000">0</span><span style="color: #000000">],&nbsp;F[y][</span><span style="color: #000000">1</span><span style="color: #000000">]);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;G[len][</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;v1&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;v1&nbsp;:&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">0</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v01&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;v1&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;v1&nbsp;:&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">1</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v02&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;v2&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;v2&nbsp;:&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">0</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;G[len][</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;minv2(v01,&nbsp;v02);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v01&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;v1&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">2</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;v1&nbsp;:&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">2</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v02&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;v2&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">?</span><span style="color: #000000">&nbsp;v2&nbsp;:&nbsp;G[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][</span><span style="color: #000000">1</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;G[len][</span><span style="color: #000000">2</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;minv2(v01,&nbsp;v02);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re(j,&nbsp;</span><span style="color: #000000">3</span><span style="color: #000000">)&nbsp;F[x][j]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;G[len][j];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re(j,&nbsp;MAXW)&nbsp;{S[</span><span style="color: #000000">0</span><span style="color: #000000">][j][</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;S[</span><span style="color: #000000">0</span><span style="color: #000000">][j][</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;S[</span><span style="color: #000000">0</span><span style="color: #000000">][j][</span><span style="color: #000000">2</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;}&nbsp;len&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E[x].next;&nbsp;p&nbsp;</span><span style="color: #000000">!=</span><span style="color: #000000">&nbsp;x;&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E[p].next)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[p].b;&nbsp;len</span><span style="color: #000000">++</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re(j,&nbsp;MAXW)&nbsp;re(k,&nbsp;</span><span style="color: #000000">3</span><span style="color: #000000">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;S[len][j][k]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(j)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sum&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;re(k0,&nbsp;</span><span style="color: #000000">3</span><span style="color: #000000">)&nbsp;{sum&nbsp;</span><span style="color: #000000">+=</span><span style="color: #000000">&nbsp;FS[y][j&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][k0];&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(sum&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;MOD)&nbsp;sum&nbsp;</span><span style="color: #000000">-=</span><span style="color: #000000">&nbsp;MOD;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;S[len][j][k]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;(sum&nbsp;</span><span style="color: #000000">*</span><span style="color: #000000">&nbsp;S[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][j][k])&nbsp;</span><span style="color: #000000">%</span><span style="color: #000000">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(k)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sum&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;re(k0,&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">)&nbsp;{sum&nbsp;</span><span style="color: #000000">+=</span><span style="color: #000000">&nbsp;FS[y][j][k0];&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(sum&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;MOD)&nbsp;sum&nbsp;</span><span style="color: #000000">-=</span><span style="color: #000000">&nbsp;MOD;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;S[len][j][k]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;(S[len][j][k]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;sum&nbsp;</span><span style="color: #000000">*</span><span style="color: #000000">&nbsp;S[len&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">][j][k&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">])&nbsp;</span><span style="color: #000000">%</span><span style="color: #000000">&nbsp;MOD;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re(j,&nbsp;MAXW)&nbsp;re(k,&nbsp;</span><span style="color: #000000">3</span><span style="color: #000000">)&nbsp;FS[x][j][k]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;S[len][j][k];<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;res1&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;minv3(F[</span><span style="color: #000000">0</span><span style="color: #000000">][</span><span style="color: #000000">0</span><span style="color: #000000">],&nbsp;F[</span><span style="color: #000000">0</span><span style="color: #000000">][</span><span style="color: #000000">1</span><span style="color: #000000">],&nbsp;F[</span><span style="color: #000000">0</span><span style="color: #000000">][</span><span style="color: #000000">2</span><span style="color: #000000">]);<br />&nbsp;&nbsp;&nbsp;&nbsp;res2&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;re(i,&nbsp;</span><span style="color: #000000">3</span><span style="color: #000000">)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(F[</span><span style="color: #000000">0</span><span style="color: #000000">][i]&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;res1)&nbsp;res2&nbsp;</span><span style="color: #000000">+=</span><span style="color: #000000">&nbsp;FS[</span><span style="color: #000000">0</span><span style="color: #000000">][F[</span><span style="color: #000000">0</span><span style="color: #000000">][i]][i];&nbsp;res2&nbsp;</span><span style="color: #000000">%=</span><span style="color: #000000">&nbsp;MOD;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;pri()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;cout&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;res1&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;endl&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;res2&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;endl;<br />}<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;main()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;init();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">!</span><span style="color: #000000">res1)&nbsp;prepare();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">!</span><span style="color: #000000">res1)&nbsp;solve();<br />&nbsp;&nbsp;&nbsp;&nbsp;pri();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />}<br /><br /></span></div><br /> <img src ="http://www.cppblog.com/MatoNo1/aggbug/191595.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2012-09-22 16:21 <a href="http://www.cppblog.com/MatoNo1/archive/2012/09/22/191595.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>【AHOI2013复仇】两道LIS模型题总结</title><link>http://www.cppblog.com/MatoNo1/archive/2012/09/08/189969.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Sat, 08 Sep 2012 12:40:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2012/09/08/189969.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/189969.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2012/09/08/189969.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/189969.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/189969.html</trackback:ping><description><![CDATA[最近做了两道LIS模型题，感觉到模型比较好，总结一下囧。<br />【1】<a title="[HAOI2007]上升序列&#13;&#10;" href="http://www.lydsy.com/JudgeOnline/problem.php?id=1046">[HAOI2007]上升序列 </a><br />预处理：设F[i]为以i开头的最长上升序列的长度，怎么求不用说了吧囧&#8230;&#8230;<br />假设目前需要求长度为M的、标号字典序最小的上升序列，显然其第一个元素A[i]必须满足F[i]&gt;=M（注意，不是等于，是大于等于！），找到满足这个条件的最小的i即可。然后，设目前已经求出了该序列的第x个元素为A[y]，则第(x+1)个元素A[z]需要满足的条件是A[z]&gt;A[y]，且F[z]=F[y]-1，找到满足这个条件的最小的z即为该序列的第(x+1)个元素。按照这种方法，扫描一遍就可以求出整个序列，时间复杂度为O(N)。如果整个序列的最长上升序列长度&lt;M，则无解。<br /><br />代码： 
<div style="border-right: #cccccc 1px solid; padding-right: 5px; border-top: #cccccc 1px solid; padding-left: 4px; font-size: 13px; padding-bottom: 4px; border-left: #cccccc 1px solid; width: 98%; word-break: break-all; padding-top: 4px; border-bottom: #cccccc 1px solid; background-color: #eeeeee"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #000000">#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">iostream</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdio.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdlib.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #0000ff">string</span><span style="color: #000000">.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br /></span><span style="color: #0000ff">using</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">namespace</span><span style="color: #000000">&nbsp;std;<br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=0;&nbsp;i&lt;n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=1;&nbsp;i&lt;=n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re2(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;r;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re3(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;=r;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n-1;&nbsp;i&gt;=0;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n;&nbsp;i&gt;0;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre2(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r-1;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre3(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;ll&nbsp;long&nbsp;long</span><span style="color: #000000"><br /></span><span style="color: #0000ff">const</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;MAXN&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">10010</span><span style="color: #000000">,&nbsp;&nbsp;&nbsp;&nbsp;MAXM&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1010</span><span style="color: #000000">,&nbsp;INF&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">~</span><span style="color: #000000">0U</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;n,&nbsp;m,&nbsp;len,&nbsp;A[MAXN],&nbsp;F[MAXN],&nbsp;D[MAXN],&nbsp;res[MAXM];<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;prepare()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;D[len&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;INF;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;l,&nbsp;r,&nbsp;mid;<br />&nbsp;&nbsp;&nbsp;&nbsp;rre(i,&nbsp;n)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;D[len])&nbsp;D[F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">++</span><span style="color: #000000">len]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;A[i];&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;len;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(l&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;r)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;mid&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;r&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;D[mid])&nbsp;l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;mid;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;mid&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;D[l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;A[i];<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;solve()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x,&nbsp;y;<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;n)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(F[i]&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;m)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;res[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;A[i];&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(m&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;&nbsp;x&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re2(j,&nbsp;i</span><span style="color: #000000">+</span><span style="color: #000000">1</span><span style="color: #000000">,&nbsp;n)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(F[j]&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;x&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;A[j]&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;res[y&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">])&nbsp;{res[y</span><span style="color: #000000">++</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;A[j];&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(y&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;m)&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;x</span><span style="color: #000000">--</span><span style="color: #000000">;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;main()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">n);&nbsp;re(i,&nbsp;n)&nbsp;scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">A[i]);<br />&nbsp;&nbsp;&nbsp;&nbsp;prepare();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;m_s;&nbsp;scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">m_s);<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;m_s)&nbsp;{scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">m);&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(m&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;len)&nbsp;puts(</span><span style="color: #000000">"</span><span style="color: #000000">Impossible</span><span style="color: #000000">"</span><span style="color: #000000">);&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{solve();&nbsp;re(j,&nbsp;m</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;printf(</span><span style="color: #000000">"</span><span style="color: #000000">%d&nbsp;</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;res[j]);&nbsp;printf(</span><span style="color: #000000">"</span><span style="color: #000000">%d\n</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;res[m&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">]);}}<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />}<br /><br /></span></div><br />【2】<a title="[HAOI2006]数字序列&#13;&#10;" href="http://www.lydsy.com/JudgeOnline/problem.php?id=1049">[HAOI2006]数字序列 </a><br />首先，由于序列的所有元素都是整数，所以可以将原序列的所有元素减去它的下标，这样就把上升序列转化为不下降序列了。<br />第一问的结果显然就是(N-新序列的最长不下降序列长度)。关键在于第二问。以下A均表示新序列。<br />设F[i]为以A[i]结尾的最长不下降序列长度（同样，求法不用说了），G[i]为在A[i]不修改的前提下将A[0..i]转变为不下降序列的最小修改量。首先求出F[i]，然后在求G[i]时，枚举上一个&#8220;不动点&#8221;（就是不修改的元素）A[j]（显然必须满足A[j]&lt;=A[i]且F[j]=F[i]-1），这样最小修改量就是G[j]+(将A[j..i]转变为不下降序列的最小修改量）。可以证明，A[j..i]的最优修改方案必然是将A[j+1..t]全部修改为A[j]，A[t+1..i]全部修改为A[i]，这里t是一个[j..i]范围的值。问题就是如何求出最优的t？<br />一开始，假设t=j，即把A[j+1..i-1]全部修改为A[i]，计算出修改量，设为S。然后，由于A[j+1..i-1]之间的元素要么小于A[j]，要么大于A[i]（这个是显然的囧），我们把小于A[j]的元素称为&#8220;小数&#8221;，把大于A[i]的元素称为&#8220;大数&#8221;，则当t取t0时，修改量为S-(A[i]-A[j])*(A[j+1..t0]中的&#8220;小数&#8221;个数减去&#8220;大数&#8221;个数）。这样，只需扫描一下，求出使得(A[j+1..t0]中的&#8220;小数&#8221;个数减去&#8220;大数&#8221;个数）值最大的t0即可。<br />当然还有一个问题，对于同一个i，满足&#8220;A[j]&lt;=A[i]且F[j]=F[i]-1&#8221;的元素个数可能有很多，如果一个一个枚举，一个一个扫描，会很慢的囧&#8230;&#8230;解决方法是，求出满足这个条件的j中最小的一个，设为j0，然后把A[j0+1..i-1]中的所有&#8220;小数&#8221;和&#8220;大数&#8221;全部处理出来，然后用类似前缀和的方法就能搞了囧&#8230;&#8230;当然，为了找到j0，需要建一个二分图，边为(F[i], i)。<br />最后，为了方便，可以把A序列的左边加一个-INF，右边加一个+INF。最后总的时间复杂度，理论上为O(N<sup>2</sup>)，但由于是随机数据，所以远远达不到这个级别。<br /><br />代码： 
<div style="border-right: #cccccc 1px solid; padding-right: 5px; border-top: #cccccc 1px solid; padding-left: 4px; font-size: 13px; padding-bottom: 4px; border-left: #cccccc 1px solid; width: 98%; word-break: break-all; padding-top: 4px; border-bottom: #cccccc 1px solid; background-color: #eeeeee"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #000000">#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">iostream</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdio.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdlib.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #0000ff">string</span><span style="color: #000000">.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br /></span><span style="color: #0000ff">using</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">namespace</span><span style="color: #000000">&nbsp;std;<br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=0;&nbsp;i&lt;n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=1;&nbsp;i&lt;=n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re2(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;r;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re3(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;=r;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n-1;&nbsp;i&gt;=0;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n;&nbsp;i&gt;0;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre2(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r-1;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;rre3(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;ll&nbsp;long&nbsp;long</span><span style="color: #000000"><br /></span><span style="color: #0000ff">const</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;MAXN&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">40010</span><span style="color: #000000">,&nbsp;INF&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">~</span><span style="color: #000000">0U</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">struct</span><span style="color: #000000">&nbsp;edge&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;a,&nbsp;b,&nbsp;pre,&nbsp;next;<br />}&nbsp;E[MAXN&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">];<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;n,&nbsp;m,&nbsp;A[MAXN],&nbsp;D[MAXN],&nbsp;F[MAXN],&nbsp;W[MAXN],&nbsp;res1;<br />ll&nbsp;G[MAXN],&nbsp;res2;<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;init_d()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;n)&nbsp;E[i].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[i].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;i;&nbsp;m&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;n;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;add_edge(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;a,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;b)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;E[m].a&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E[m].b&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;b;&nbsp;E[m].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[a].pre;&nbsp;E[m].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a;&nbsp;E[a].pre&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m;&nbsp;E[E[m].pre].next&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;m</span><span style="color: #000000">++</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;init()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">n);<br />&nbsp;&nbsp;&nbsp;&nbsp;A[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">INF;&nbsp;re1(i,&nbsp;n)&nbsp;{scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">A[i]);&nbsp;A[i]&nbsp;</span><span style="color: #000000">-=</span><span style="color: #000000">&nbsp;i;}&nbsp;A[</span><span style="color: #000000">++</span><span style="color: #000000">n]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;INF;&nbsp;n</span><span style="color: #000000">++</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;solve()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;init_d();&nbsp;F[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;G[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;D[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">INF;&nbsp;add_edge(</span><span style="color: #000000">0</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">);&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;len&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">,&nbsp;l,&nbsp;r,&nbsp;mid,&nbsp;x,&nbsp;maxw;&nbsp;ll&nbsp;sum,&nbsp;tmp;<br />&nbsp;&nbsp;&nbsp;&nbsp;re2(i,&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">,&nbsp;n)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;D[len])&nbsp;D[F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">++</span><span style="color: #000000">len]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;A[i];&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;len;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(l&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;r)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;mid&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;r&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;D[mid])&nbsp;l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;mid;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;mid&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;D[F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">++</span><span style="color: #000000">l]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;A[i];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E[F[i]</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">].next;&nbsp;;&nbsp;p</span><span style="color: #000000">=</span><span style="color: #000000">E[p].next)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">&gt;=</span><span style="color: #000000">&nbsp;A[x&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;E[p].b])&nbsp;</span><span style="color: #0000ff">break</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;W[x]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;re2(j,&nbsp;x</span><span style="color: #000000">+</span><span style="color: #000000">1</span><span style="color: #000000">,&nbsp;i)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[j]&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;A[i])&nbsp;W[j]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;W[j&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;W[j]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;W[j&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sum&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;maxw&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">INF;&nbsp;G[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">~</span><span style="color: #000000">0Ull&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rre2(j,&nbsp;i,&nbsp;x)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[j]&nbsp;</span><span style="color: #000000">&lt;=</span><span style="color: #000000">&nbsp;A[i]&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;F[j]&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;F[i]&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tmp&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;G[j]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;sum;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(tmp&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;G[i])&nbsp;G[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;tmp;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;tmp&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;G[j]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;sum&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;(ll)&nbsp;(maxw&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;W[j])&nbsp;</span><span style="color: #000000">*</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;A[j]);&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(tmp&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;G[i])&nbsp;G[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;tmp;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[j]&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;A[i])&nbsp;sum&nbsp;</span><span style="color: #000000">+=</span><span style="color: #000000">&nbsp;A[j]&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;A[i];&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;sum&nbsp;</span><span style="color: #000000">+=</span><span style="color: #000000">&nbsp;A[i]&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;A[j];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(W[j]&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;maxw)&nbsp;maxw&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;W[j];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;add_edge(F[i],&nbsp;i);<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;res1&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;n&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;F[n&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;res2&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;G[n&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">];<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;pri()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;cout&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;res1&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;endl&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;res2&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;endl;<br />}<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;main()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;init();<br />&nbsp;&nbsp;&nbsp;&nbsp;solve();<br />&nbsp;&nbsp;&nbsp;&nbsp;pri();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />}<br /><br /></span></div><br /><img src ="http://www.cppblog.com/MatoNo1/aggbug/189969.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2012-09-08 20:40 <a href="http://www.cppblog.com/MatoNo1/archive/2012/09/08/189969.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>炮兵阵地以及与其相关的一类状压DP问题</title><link>http://www.cppblog.com/MatoNo1/archive/2012/03/10/167626.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Sat, 10 Mar 2012 15:27:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2012/03/10/167626.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/167626.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2012/03/10/167626.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/167626.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/167626.html</trackback:ping><description><![CDATA[<div><a title="原题地址" href="http://poj.org/problem?id=1185">原题地址</a><br />说实话我第一次尝试写炮兵阵地是在2009年&#8230;&#8230;已经过去两年多了，终于找到了一个好的解法&#8230;&#8230;庆祝一下&#8230;&#8230;<br /><br />【状态压缩DP】<br />所谓状态压缩DP，就是对于某些DP问题，每一阶段的状态都有很多维，要利用某些手段将它们压缩到一维（一个正整数），顺便进行状态的精简（去掉不合法的状态），然后再进行DP。这里讲的主要是传统的状压DP，有一种基于&#8220;插头&#8221;的DP，更高级，以后再搞。<br />对于本题，可以设计出一个这样的状态：[0..1][0..1][0..1]...[0..1]（有M个[0..1]），表示该行的每个格子放不放炮兵，如果放，为1，否则为0。显然，这是一个M位二进制数，如果能把它们压缩成一个int就好了。<br /><br />【如何压缩】<br />第一个问题是这么多维的状态如何压缩的问题。<br />对于本题，由于是二进制数，直接压缩就可以了。但是对于某些情况，状态是个三进制数（每个格子的属性都有3种）甚至更多进制数，这样，直接压缩会导致无法使用位运算，从而使&#8220;解压&#8221;变得很麻烦，耗时也很长（需要暴力），因此，可以将每位三进制都拆成两位二进制：<br />0-&gt;00<br />1-&gt;01<br />2-&gt;10<br />（当然1拆成10、2拆成11也木有问题，只要能区分开就行了）<br />这样，每个状态就可以用2个二进制数来表示，可以在构造出所有合法状态以后将每个状态所对应的两位二进制数存到struct里面，使用时调出即可。<br /><br />【如何精简】<br />这个问题是最重要的，因为，如果不精简，在枚举状态以及转移的时候就会枚举到很多不合法状态，导致时间浪费。<br />所谓精简，是指在预处理以及DP过程中，尽量避开不合法状态。<br />（1）预处理中的精简：<br />包括3个部分：<br />&lt;1&gt;找到所有可能的合法状态并编号：根据题意限制，有的状态在阶段内就不合法（比如本题，一行一阶段，那么凡是有两个1位的距离小于2的状态都不合法），而且这种状态所占的比重往往还很大（本题中，M=10时，也只有60种可能的合法状态），此时，为了找到这些合法状态，可以DFS构造实现。<br />需要注意的是，有的题不光要找到一个阶段内的合法状态，还要找到两个或两个以上阶段内的合法状态（比如那个有关多米诺骨牌的题），此时需要两个int同时DFS；<br />在找到合法状态以后，需要对每个合法状态进行编号，以达到&#8220;压缩&#8221;的目的。这里就涉及到了状态编号和状态表示的问题：比如，状态1001，表示为9，在DFS中第一个被搜到，因此编号为0，不要搞混了这两个（尤其不要搞混&#8220;编号为0&#8221;和&#8220;状态表示为0&#8221;，它们是不同的）。在预处理和DP的过程中，所有涉及到状态的数组下标，全部是编号而不是表示，知道编号要求表示，可以在DFS中记录的数组里面调，而知道表示要求编号，可以利用逆数组或者哈希；<br />&lt;2&gt;找到每一阶段的合法状态：即使是&lt;1&gt;中被判定为合法的状态，在具体的各个阶段中也未必合法（比如本题，如果某一行的某一个位置是'H'，不能放，而某一个状态在这里放了，则不合法），因此要对每个阶段再枚举一遍，找到真正合法的状态，并计入一个vector；<br />&lt;3&gt;找到状态转移中的合法状态：在状态转移中，往往要求状态不冲突（比如本题，在连续的三个阶段中，都不能有某一位有两个为1的情况），因此，还要枚举每个状态在转移时与其不冲突的状态，并计入vector。<br />注意，有时候这一步不是很容易进行，需要在DP过程中进行；<br />（2）DP过程中的精简：<br />DP过程中，枚举状态、转移决策都只枚举合法的，在vector里面调（注意vector里记录的全都是状态编号而不是表示！），可以大大减少枚举量，不过有时候，还会有一些时间浪费，这时候，可以采取一些其它的办法来精简，比如再次进行DFS构造合法状态等。<br /><br />总之，这类问题的目标就是&#8220;精简，精简，再精简，使枚举到的不合法状态减到最少&#8221;。<br /></div>代码：<br /><div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #000000; ">#include&nbsp;</span><span style="color: #000000; ">&lt;</span><span style="color: #000000; ">iostream</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; "><br />#include&nbsp;</span><span style="color: #000000; ">&lt;</span><span style="color: #000000; ">stdio.h</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; "><br />#include&nbsp;</span><span style="color: #000000; ">&lt;</span><span style="color: #000000; ">stdlib.h</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; "><br />#include&nbsp;</span><span style="color: #000000; ">&lt;</span><span style="color: #0000FF; ">string</span><span style="color: #000000; ">.h</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; "><br />#include&nbsp;</span><span style="color: #000000; ">&lt;</span><span style="color: #000000; ">vector</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">using</span><span style="color: #000000; ">&nbsp;</span><span style="color: #0000FF; ">namespace</span><span style="color: #000000; ">&nbsp;std;<br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;re(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=0;&nbsp;i&lt;n;&nbsp;i++)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;re1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=1;&nbsp;i&lt;=n;&nbsp;i++)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;re2(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;r;&nbsp;i++)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;re3(i,&nbsp;l,&nbsp;r)&nbsp;for&nbsp;(int&nbsp;i=l;&nbsp;i&lt;=r;&nbsp;i++)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;rre(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n-1;&nbsp;i&gt;=0;&nbsp;i--)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;rre1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=n;&nbsp;i&gt;0;&nbsp;i--)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;rre2(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r-1;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;rre3(i,&nbsp;r,&nbsp;l)&nbsp;for&nbsp;(int&nbsp;i=r;&nbsp;i&gt;=l;&nbsp;i--)</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;pb&nbsp;push_back</span><span style="color: #000000; "><br /></span><span style="color: #0000FF; ">#define</span><span style="color: #000000; ">&nbsp;IR&nbsp;iterator</span><span style="color: #000000; "><br />typedef&nbsp;vector&nbsp;</span><span style="color: #000000; ">&lt;</span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; ">&nbsp;vi;<br /></span><span style="color: #0000FF; ">const</span><span style="color: #000000; ">&nbsp;</span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;MAXN&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">103</span><span style="color: #000000; ">,&nbsp;MAXM&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">11</span><span style="color: #000000; ">,&nbsp;MAXS&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">100</span><span style="color: #000000; ">,&nbsp;INF&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">~</span><span style="color: #000000; ">0U</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">&gt;&gt;</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">2</span><span style="color: #000000; ">;<br /></span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;n,&nbsp;m,&nbsp;S,&nbsp;A[MAXN],&nbsp;B[MAXS],&nbsp;T1[MAXS],&nbsp;F[MAXN][MAXS][MAXS],&nbsp;res;<br /></span><span style="color: #0000FF; ">bool</span><span style="color: #000000; ">&nbsp;F0[MAXN][MAXS];<br />vi&nbsp;P0[MAXN],&nbsp;P1[MAXS][MAXS];<br /></span><span style="color: #0000FF; ">void</span><span style="color: #000000; ">&nbsp;init()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;scanf(</span><span style="color: #000000; ">"</span><span style="color: #000000; ">%d%d</span><span style="color: #000000; ">"</span><span style="color: #000000; ">,&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">n,&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">m);&nbsp;getchar();<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;{A[i]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">;&nbsp;re(j,&nbsp;m)&nbsp;A[i]&nbsp;</span><span style="color: #000000; ">|=</span><span style="color: #000000; ">&nbsp;((getchar()&nbsp;</span><span style="color: #000000; ">==</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">'</span><span style="color: #000000; ">P</span><span style="color: #000000; ">'</span><span style="color: #000000; ">)&nbsp;</span><span style="color: #000000; ">&lt;&lt;</span><span style="color: #000000; ">&nbsp;j);&nbsp;getchar();}<br />}<br /></span><span style="color: #0000FF; ">void</span><span style="color: #000000; ">&nbsp;dfs(</span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;v,&nbsp;</span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;ST)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(v&nbsp;</span><span style="color: #000000; ">&gt;=</span><span style="color: #000000; ">&nbsp;m)&nbsp;B[S</span><span style="color: #000000; ">++</span><span style="color: #000000; ">]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;ST;&nbsp;</span><span style="color: #0000FF; ">else</span><span style="color: #000000; ">&nbsp;{dfs(v&nbsp;</span><span style="color: #000000; ">+</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">3</span><span style="color: #000000; ">,&nbsp;ST&nbsp;</span><span style="color: #000000; ">|</span><span style="color: #000000; ">&nbsp;(</span><span style="color: #000000; ">1</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">&lt;&lt;</span><span style="color: #000000; ">&nbsp;v));&nbsp;dfs(v&nbsp;</span><span style="color: #000000; ">+</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">,&nbsp;ST);}<br />}<br /></span><span style="color: #0000FF; ">void</span><span style="color: #000000; ">&nbsp;prepare()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;S&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">;&nbsp;dfs(</span><span style="color: #000000; ">0</span><span style="color: #000000; ">,&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">);<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;S)&nbsp;{T1[i]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">;&nbsp;</span><span style="color: #0000FF; ">for</span><span style="color: #000000; ">&nbsp;(</span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;j</span><span style="color: #000000; ">=</span><span style="color: #000000; ">B[i];&nbsp;j;&nbsp;j</span><span style="color: #000000; ">-=</span><span style="color: #000000; ">j</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">(</span><span style="color: #000000; ">-</span><span style="color: #000000; ">j))&nbsp;T1[i]</span><span style="color: #000000; ">++</span><span style="color: #000000; ">;}<br />&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;re(j,&nbsp;S)&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(</span><span style="color: #000000; ">!</span><span style="color: #000000; ">(</span><span style="color: #000000; ">~</span><span style="color: #000000; ">A[i]&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">&nbsp;B[j]))&nbsp;{P0[i].pb(j);&nbsp;F0[i][j]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">;}&nbsp;P0[</span><span style="color: #000000; ">0</span><span style="color: #000000; ">].pb(S&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">);&nbsp;F0[</span><span style="color: #000000; ">0</span><span style="color: #000000; ">][S&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">;<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;S)&nbsp;re(j,&nbsp;S)&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(</span><span style="color: #000000; ">!</span><span style="color: #000000; ">(B[i]&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">&nbsp;B[j]))&nbsp;re(k,&nbsp;S)&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(</span><span style="color: #000000; ">!</span><span style="color: #000000; ">(B[i]&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">&nbsp;B[k])&nbsp;</span><span style="color: #000000; ">&amp;&amp;</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">!</span><span style="color: #000000; ">(B[j]&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">&nbsp;B[k]))&nbsp;P1[i][j].pb(k);<br />}<br /></span><span style="color: #0000FF; ">void</span><span style="color: #000000; ">&nbsp;solve()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;re3(i,&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">,&nbsp;n)&nbsp;re(j1,&nbsp;S)&nbsp;re(j2,&nbsp;S)&nbsp;F[i][j1][j2]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">INF;&nbsp;F[</span><span style="color: #000000; ">0</span><span style="color: #000000; ">][S&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">][S&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">;<br />&nbsp;&nbsp;&nbsp;&nbsp;vi::IR&nbsp;vi_e0,&nbsp;vi_e1,&nbsp;vi_e2;&nbsp;</span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;j0,&nbsp;j1,&nbsp;k,&nbsp;V;<br />&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;n)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vi_e0&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;P0[i].end();&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(i)&nbsp;vi_e1&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;P0[i&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">].end();&nbsp;</span><span style="color: #0000FF; ">else</span><span style="color: #000000; ">&nbsp;vi_e1&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;P0[i].end();<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">for</span><span style="color: #000000; ">&nbsp;(vi::IR&nbsp;p</span><span style="color: #000000; ">=</span><span style="color: #000000; ">P0[i].begin();&nbsp;p&nbsp;</span><span style="color: #000000; ">!=</span><span style="color: #000000; ">&nbsp;vi_e0;&nbsp;p</span><span style="color: #000000; ">++</span><span style="color: #000000; ">)<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">for</span><span style="color: #000000; ">&nbsp;(vi::IR&nbsp;p_</span><span style="color: #000000; ">=</span><span style="color: #000000; ">P0[i&nbsp;</span><span style="color: #000000; ">?</span><span style="color: #000000; ">&nbsp;i&nbsp;</span><span style="color: #000000; ">-</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">&nbsp;:&nbsp;i].begin();&nbsp;p_&nbsp;</span><span style="color: #000000; ">!=</span><span style="color: #000000; ">&nbsp;vi_e1;&nbsp;p_</span><span style="color: #000000; ">++</span><span style="color: #000000; ">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;j0&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">*</span><span style="color: #000000; ">p;&nbsp;j1&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">*</span><span style="color: #000000; ">p_;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(</span><span style="color: #000000; ">!</span><span style="color: #000000; ">(B[j0]&nbsp;</span><span style="color: #000000; ">&amp;</span><span style="color: #000000; ">&nbsp;B[j1]))&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vi_e2&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;P1[j0][j1].end();<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">for</span><span style="color: #000000; ">&nbsp;(vi::IR&nbsp;p__&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;P1[j0][j1].begin();&nbsp;p__&nbsp;</span><span style="color: #000000; ">!=</span><span style="color: #000000; ">&nbsp;vi_e2;&nbsp;p__</span><span style="color: #000000; ">++</span><span style="color: #000000; ">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;k&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">*</span><span style="color: #000000; ">p__;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(F0[i&nbsp;</span><span style="color: #000000; ">+</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">][k])&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;V&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;F[i][j0][j1]&nbsp;</span><span style="color: #000000; ">+</span><span style="color: #000000; ">&nbsp;T1[k];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(V&nbsp;</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; ">&nbsp;F[i&nbsp;</span><span style="color: #000000; ">+</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">][k][j0])&nbsp;F[i&nbsp;</span><span style="color: #000000; ">+</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">1</span><span style="color: #000000; ">][k][j0]&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;V;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;res&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">;&nbsp;re(i,&nbsp;S)&nbsp;re(j,&nbsp;S)&nbsp;</span><span style="color: #0000FF; ">if</span><span style="color: #000000; ">&nbsp;(F[n][i][j]&nbsp;</span><span style="color: #000000; ">&gt;</span><span style="color: #000000; ">&nbsp;res)&nbsp;res&nbsp;</span><span style="color: #000000; ">=</span><span style="color: #000000; ">&nbsp;F[n][i][j];<br />}<br /></span><span style="color: #0000FF; ">void</span><span style="color: #000000; ">&nbsp;pri()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;printf(</span><span style="color: #000000; ">"</span><span style="color: #000000; ">%d\n</span><span style="color: #000000; ">"</span><span style="color: #000000; ">,&nbsp;res);<br />}<br /></span><span style="color: #0000FF; ">int</span><span style="color: #000000; ">&nbsp;main()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;init();<br />&nbsp;&nbsp;&nbsp;&nbsp;prepare();<br />&nbsp;&nbsp;&nbsp;&nbsp;solve();<br />&nbsp;&nbsp;&nbsp;&nbsp;pri();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000FF; ">return</span><span style="color: #000000; ">&nbsp;</span><span style="color: #000000; ">0</span><span style="color: #000000; ">;<br />}<br /></span></div><img src ="http://www.cppblog.com/MatoNo1/aggbug/167626.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2012-03-10 23:27 <a href="http://www.cppblog.com/MatoNo1/archive/2012/03/10/167626.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>KMP、AC自动机在字符串匹配类动态规划问题中的应用</title><link>http://www.cppblog.com/MatoNo1/archive/2011/10/30/159339.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Sun, 30 Oct 2011 03:22:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2011/10/30/159339.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/159339.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2011/10/30/159339.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/159339.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/159339.html</trackback:ping><description><![CDATA[有一类动态规划（其中也包含递推）问题，要求满足一些限制条件的字符串，这些限制条件是&#8220;需要含有某个子串&#8221;或&#8220;不能含有某个子串&#8221;，那么KMP、AC自动机等就有大用了。<br /><br />【例1】<a title="HDU3689" href="http://acm.hdu.edu.cn/showproblem.php?pid=3689">HDU3689</a><br />题意：字符集中有一些字符，给出每个字符的出现概率（它们的和保证为1），再给出一个子串B，求：任给一个长度为N的字符串A（只能包含字符集中的字符），使得S是A的子串的概率。<br /><br />求解这类问题首先要进行补集转化。因为子串可能有重叠（比如"ababa"中就出现了两个"aba"），所以先转化为&#8220;求任给一个长度为N的字符串A（只能包含字符集中的字符），使得<span style="color: red"><strong>B不是A的子串</strong></span>的概率&#8221;，然后再用1减去这个概率即为结果。<br />设F[i][j]为&#8220;在所有长度为i的<span style="color: red"><strong>不出现B</strong></span>的字符串中，后缀与B的前缀匹配长度为j（即该字符串的后缀与B的前缀的<span style="color: red"><strong>最大</strong></span>匹配长度为j）的概率&#8221;，很显然，F是由递推得到了，关键是如何进行状态转移？或者说，在递推过程中，哪些状态可能成为F[i][j]的前趋状态？<br />假设F[i-1][k]是F[i][j]的前趋状态，也就是说，<span style="color: red"><strong>在字符集中至少存在一个字符c，使得主串的第i位（最后一位）取c时，能够从F[i-1][k]转移到F[i][j]</strong></span>。这就需要求一个值S[k][c]，表示当主串的后缀与B的前缀的（最大）匹配长度为k时，在主串后再加上一个字符c，其匹配长度会变成什么。举例：设目前主串A'="abasab"，B="asabs"，其匹配长度为4，若在A'后加上一个字符's'，则匹配长度变为5，所以S[4]['s']=5，而若在A'后加上一个字符'a'，则匹配长度会变成1，所以S[4]['a']=1。显然S值和A前面的哪些字符是没有关系的。<br />那么这个S值如何计算？其实可以发现，S和KMP算法中的nx数组神似，因此完全可以按照计算nx数组的办法来计算S。具体来说，先要对B作KMP自身匹配，求出其nx数组，然后，在求S[k][c]的时候，尝试在B的第k位（由于B的下标从0开始所以B[k-1]）后加上字符c，看看会&#8220;回退&#8221;到哪里即可。代码： 
<div style="border-right: #cccccc 1px solid; padding-right: 5px; border-top: #cccccc 1px solid; padding-left: 4px; font-size: 13px; padding-bottom: 4px; border-left: #cccccc 1px solid; width: 98%; word-break: break-all; padding-top: 4px; border-bottom: #cccccc 1px solid; background-color: #eeeeee"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #000000">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;j&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;nx[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re2(i,&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">,&nbsp;m)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(j&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;A[i]&nbsp;</span><span style="color: #000000">!=</span><span style="color: #000000">&nbsp;A[j])&nbsp;j&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;nx[j&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[i]&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;A[j])&nbsp;j</span><span style="color: #000000">++</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;nx[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;j;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;re(i,&nbsp;m)&nbsp;re(k,&nbsp;SZ)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;j&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;i;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(j&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;A[j]&nbsp;</span><span style="color: #000000">!=</span><span style="color: #000000">&nbsp;k&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">97</span><span style="color: #000000">)&nbsp;j&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;nx[j&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">];<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(A[j]&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;k&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">97</span><span style="color: #000000">)&nbsp;S[i][k]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">++</span><span style="color: #000000">j;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;S[i][k]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}</span></div>这里m是B的长度。注意，当i=m时，S[i][j]是无意义的，因为前面已经说过了不能出现B。<br />在求出S值后就能求出F值了。对于状态F[i][j]，若存在一个字符c使得x=S[i][c]（满足0&lt;=x&lt;m），则F[i][j]是F[i+1][x]的前趋状态。当然，由于本题是求概率而不是求总数，且每个字符出现的概率还不一样，所以转移的时候，应是将F[i+1][x]加上F[i][j]*P[c]（P[c]是字符c出现的概率），边界：F[0][0]=1，F[0][1..m-1]均为0。<br />最终结果为1-&#8721;F[N][0..m-1]。<br /><br /><a title="代码" href="http://www.ideone.com/CDcNk">代码</a><br /><br />【例2】<a title="PKU1625" href="http://poj.org/problem?id=1625">PKU1625</a>（<a title="URAL1158" href="http://acm.timus.ru/problem.aspx?space=1&amp;num=1158">URAL1158</a>）<br />题意：给出一些子串，求长度为N，各个字符都属于给定的字符集的所有字符串中，不包含任何一个给出的子串的字符串个数（需要使用压9位的高精度）。<br /><br />本题显然是【例1】的多子串形式，而用来解决多个字符串同时匹配的只有AC自动机，那么如何在本题中使用AC自动机求解呢？<br />观察【例1】中的F[i][j]，可以想象一下，一个图中有m个顶点，分别表示匹配长度为0..(m-1)，然后不断新加入的字符让这些状态在这些结点间不断转移（状态转移就是图中的边），这样，F[i][<span>j]就表示&#8220;阶段i到达结点j上&#8221;。而AC自动</span><span>机是基于Trie（树）的，</span><span>其中有现成</span><span>的结</span><span>点，这就揭示了本题的状</span><span>态</span><span><strong>：</strong></span><br /><span>F[i][j]</span><span>表</span><span>示</span><strong><span style="color: #ff0000">长度为i的合法的字符串（就是满足字符集限制且不包含任何一个给定子串）中，在匹配到最后一位（</span></strong><strong style="color: #ff0000">第i位）后，刚好到达结点j的字符串的</strong><strong style="color: #ff0000">个数</strong>。<br />同样，S[k][c]表示&#8220;目前到达结点k，接下来的一个字符是c的时候，会到达哪个结点。在对所有的子串建立了自动机之后，S值只要类似地搞就能求出来了。然后F的转移也就搞定了。<br />不过，本题要万分注意AC自动机的一个BUG：在建立了自动机以后，需要把所有本身不危险（如果一个结点代表的字符串刚好是某一个给出的不能出现的子串，则该结点是危险结点），但通过失败指针不断上溯能够到达一个危险结点的结点，也标记为危险结点，比如两个子串是"abcde"和"bc"，则代表"abcd"的那个结点由于包含了"bc"所以也是危险的。<br />此外，本题的输入要注意，字符集的ASCII码范围是-128~127，所以必须用char而不是unsigned char，且由于可能包含空格所以必须用gets()而不是scanf()输入，又因为C/C++中木有负数下标，因此在输入之后还要转化一下（加128）。<br /><br /><a title="代码" href="http://www.ideone.com/MHp6H">代码</a><br /><br />【例3】<a title="PKU3691" href="http://poj.org/problem?id=3691">PKU3691</a><br />题意：给出一些子串和一个字符串A（其每个字符均属于字符集{'A', 'C', 'G', 'T'}），求至少要改动A的几个字符（不能改成不属于字符集的字符），使得它不包含任何一个给出的子串，若不管怎么改都不行，则结果为-1。<br /><br />这就是真正的DP了。设F[i][j]为前i位，到达的结点为j，最少改动的字符个数，则转移方程为<br />F[i][j] = min{F[i-1][x] + (A[i] != c)}，c&#8712;{'A', 'C', 'G', 'T'}，S[x][c]=j。边界：F[0][root]=0，其余的F[0][]=+&#8734;，A的实际下标从1开始。<br />求S数组的方法见【例2】<br /><br /><a title="代码" href="http://www.ideone.com/JrEIY">代码</a><br /><br />【例4】<a title="PKU3208" href="http://poj.org/problem?id=3208">PKU3208</a><br />题意：含有连续的三个数字6的正整数，称为"beastly number"，求第P个（1&lt;=P&lt;=50000000）"beastly number"（其位数不会超过15位）。<br />（这题是本沙茶在PKU上至今为止，自己想出算法的AC人数最少的题）<br />本题其实是用不着KMP的，因为"666"这样简单的子串&#8230;&#8230;<br /><br />思路：由于位数不会超过15位（后来发现最多只有10位），所以每个"beastly number"都可以看成一个长度为15，字符集为['0'..'9']的字符串（注意是可以有前导0的，因为位数可能不足15位）A，整个过程也就是从高位（第0位）向低位（第14位）求出A的各位。<br /><br />预处理：求出F[i][j]，表示若A的前i位已经确定（其中不含"666"，准确来说是非末尾不含"666"），且前i位的末尾刚好有j个'6'（j的范围是0到3）时，有多少个"beastly number"（注意，前i位既然已经确定，就不可更改了，能够决定的只有第i位的后面）。<br />显然先要求出F0[i][j]表示有多少个不是"beastly number"。其递推方程不好写，见代码（其实也是很好理解的）。然后F[i][j]=10<sup>14-i</sup> - F0[i][j]。<br /><br />然后就是不断调整边界来构造了。准确来说，设前i-1位已经确定，现在要确定第i位，则枚举第i位是0~9中的哪个值，然后求出满足条件的最小的"beastly number"和最大的"beastly number"的名次（注意，名次是从1开始的），看看P在不在其中，这样就能确定了。严重注意：如果已确定的位数中已经出现了"666"，接下来的就不用枚举了，直接在后面接上P-L就行了，L为左边界。<br /><br />但是，为什么要把本题放在KMP的专题里面呢囧？<span>因为如果这个子串不是"666"而是一些结构复</span><span>杂的东东比如"123131"这样的，只有借助K</span><span>MP算法了。这时，F[i][j]就表示 A的前i位已经确定（非末尾不含这个子串），且其后缀与这个子串的前缀匹</span><span>配长度为</span><span>j，</span>有多少个"beastly number" ，转移方程与前几个例子类似。<br /><br /><a title="代码" href="http://www.ideone.com/Areon">代码</a><br /><br />总结：<br />KMP算法和AC自动机的状态转移性质决定了它们在字符串匹配类DP问题中的巨大作用。在实际应用中，要注意灵活使用它们。此外，AC自动机的那个BUG是一定要注意的。 <img src ="http://www.cppblog.com/MatoNo1/aggbug/159339.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2011-10-30 11:22 <a href="http://www.cppblog.com/MatoNo1/archive/2011/10/30/159339.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>PKU3017</title><link>http://www.cppblog.com/MatoNo1/archive/2011/07/08/150454.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Fri, 08 Jul 2011 04:40:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2011/07/08/150454.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/150454.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2011/07/08/150454.html#Feedback</comments><slash:comments>1</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/150454.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/150454.html</trackback:ping><description><![CDATA[<div>【原题见<a title="这里" href="http://poj.org/problem?id=3017">这里</a>】<br /><br />本沙茶见过的最猥琐的DP题啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊啊&#8230;&#8230;<br /><br />设F[i]为将A[1..i]拆分成若干段的最大值最小和，则有<br />F[i]=min{F[j] +&nbsp;max[j+1, i]}（B[i]&lt;=j&lt;i），其中max[j+1, i]表示A[j+1..i]中的最大值，B[i]表示从i向左最远可以延伸到哪里（也就是满足SUM[x..i]&lt;=m的最小的x值）。B数组可以通过预处理在O(N)时间内得到。<br />边界：F[0]=0。<br /><br />下面是优化过程。JZP神犇的论文里面已经够详细了。这里只是简要说明一下。<br />首先容易证明，F是单调递增的。<br />然后一个很关键的定理是：<strong style="color: red">若F[i]的最优决策为j，则有A[j]&gt;&#8704;A[k]（j&lt;k&lt;=i）。</strong><br />证明：用反证法。若A[j+1..i]中存在不小于A[j]的值，则可得max[j..i]=max[j+1..i]，又因为F单调递增，所以F[j-1]+max[j..i]&lt;=F[j]+max[j+1.i]，即决策(j-1)一定不比决策j差，也就是决策j不可能成为最优决策。<br />这样，可以维护一个下标严格递增、A值严格递减的队列Q（即对于队列中的任意两个元素Q[i]和Q[j]，若i&lt;j，则Q[i].pos&lt;Q[j].pos且A[Q[i].pos]&gt;A[Q[j].pos]，具体实现时pos可省略）。则可能成为最优决策的决策要么是在这个队列Q里，要么是B[i]。对于队列中的某个决策Q[x]，该决策导出的值为F[Q[x]]+A[Q[x + 1]]（很容易证明max[Q[x]+1..i]=A[Q[x + 1]]），找到这些导出的值中的最小值即可（注意，队尾元素没有导出值）。对于决策B[i]，只需要在预处理的时候同时得到MAX[i]=max[B[i]+1..i]即可（也可以在O(N)时间内得到），决策B[i]导出的值为F[B[i]]+MAX[i]。<br />在删除队首过时元素的时候，需要把导出值也删除，删除队尾元素也一样，插入的时候，若插入前队列不为空，则需要插入一个导出值。也就是，需要一个支持在对数时间内进行插入、删除任意结点、找最小值等操作，显然用平衡树最好。<br /><br />注意事项：<br />（1）不管是在队首删除还是在队尾删除，若删除的是队列中的最后一个元素，则不需要在平衡树中删除导出值；<br />（2）插入时，若插入前队列为空，则不需要在平衡树中插入导出值；<br />（3）在计算F[i]时，应先将决策i压入。<br /><br />代码：
<div style="border-right: #cccccc 1px solid; padding-right: 5px; border-top: #cccccc 1px solid; padding-left: 4px; font-size: 13px; padding-bottom: 4px; border-left: #cccccc 1px solid; width: 98%; word-break: break-all; padding-top: 4px; border-bottom: #cccccc 1px solid; background-color: #eeeeee"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #000000">#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">iostream</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br />#include&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">stdio.h</span><span style="color: #000000">&gt;</span><span style="color: #000000"><br /></span><span style="color: #0000ff">using</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">namespace</span><span style="color: #000000">&nbsp;std;<br /></span><span style="color: #0000ff">#define</span><span style="color: #000000">&nbsp;re1(i,&nbsp;n)&nbsp;for&nbsp;(int&nbsp;i=1;&nbsp;i&lt;=n;&nbsp;i++)</span><span style="color: #000000"><br /></span><span style="color: #0000ff">const</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;MAXN&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">100001</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">struct</span><span style="color: #000000">&nbsp;node&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;l,&nbsp;r,&nbsp;p,&nbsp;sz0,&nbsp;sz,&nbsp;mul;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;v;<br />}&nbsp;T[MAXN];<br /></span><span style="color: #0000ff">const</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;INF&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">~</span><span style="color: #000000">0Ull&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;n,&nbsp;N&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">,&nbsp;a[MAXN],&nbsp;b[MAXN],&nbsp;MAX[MAXN],&nbsp;Q[MAXN],&nbsp;front&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">,&nbsp;rear&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">,&nbsp;root&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;m,&nbsp;F[MAXN],&nbsp;res&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;init()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;cin&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;n&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;m;<br />&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;scanf(</span><span style="color: #000000">"</span><span style="color: #000000">%d</span><span style="color: #000000">"</span><span style="color: #000000">,&nbsp;</span><span style="color: #000000">&amp;</span><span style="color: #000000">a[i]);&nbsp;a[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">~</span><span style="color: #000000">0U</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">&gt;&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">2</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;prepare()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(a[i]&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;m)&nbsp;{res&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;}<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;sum&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(sum</span><span style="color: #000000">+=</span><span style="color: #000000">a[i];&nbsp;sum</span><span style="color: #000000">&gt;</span><span style="color: #000000">m;&nbsp;sum</span><span style="color: #000000">-=</span><span style="color: #000000">a[x</span><span style="color: #000000">++</span><span style="color: #000000">])&nbsp;;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;b[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;x&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(;&nbsp;front</span><span style="color: #000000">&lt;=</span><span style="color: #000000">rear&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;Q[front]</span><span style="color: #000000">&lt;=</span><span style="color: #000000">b[i];&nbsp;front</span><span style="color: #000000">++</span><span style="color: #000000">)&nbsp;;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(;&nbsp;front</span><span style="color: #000000">&lt;=</span><span style="color: #000000">rear&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;a[Q[rear]]</span><span style="color: #000000">&lt;=</span><span style="color: #000000">a[i];&nbsp;rear</span><span style="color: #000000">--</span><span style="color: #000000">)&nbsp;;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Q[</span><span style="color: #000000">++</span><span style="color: #000000">rear]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;i;&nbsp;MAX[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;a[Q[front]];<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;vst(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(x)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;cout&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;T[x].v&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">'</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">'</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;vst(T[x].l);&nbsp;vst(T[x].r);<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;slc(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;_p,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;_c)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;T[_p].l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;_c;&nbsp;T[_c].p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;_p;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;src(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;_p,&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;_c)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;T[_p].r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;_c;&nbsp;T[_c].p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;_p;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;upd(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;T[x].sz0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[T[x].l].sz0&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;T[T[x].r].sz0&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;T[x].mul;<br />&nbsp;&nbsp;&nbsp;&nbsp;T[x].sz&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[T[x].l].sz&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;T[T[x].r].sz&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;lrot(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].p;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(y&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;root)&nbsp;T[root&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;x].p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[y].p;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(y&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;T[p].l)&nbsp;slc(p,&nbsp;x);&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;src(p,&nbsp;x);}<br />&nbsp;&nbsp;&nbsp;&nbsp;src(y,&nbsp;T[x].l);&nbsp;slc(x,&nbsp;y);&nbsp;T[x].sz0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[y].sz0;&nbsp;T[x].sz&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[y].sz;&nbsp;upd(y);<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;rrot(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].p;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(y&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;root)&nbsp;T[root&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;x].p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[y].p;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(y&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;T[p].l)&nbsp;slc(p,&nbsp;x);&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;src(p,&nbsp;x);}<br />&nbsp;&nbsp;&nbsp;&nbsp;slc(y,&nbsp;T[x].r);&nbsp;src(x,&nbsp;y);&nbsp;T[x].sz0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[y].sz0;&nbsp;T[x].sz&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[y].sz;&nbsp;upd(y);<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;maintain(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x,&nbsp;</span><span style="color: #0000ff">bool</span><span style="color: #000000">&nbsp;ff)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;z;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(ff)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(T[T[T[x].r].r].sz&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;T[T[x].l].sz)&nbsp;{z&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].r;&nbsp;lrot(z);}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(T[T[T[x].r].l].sz&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;T[T[x].l].sz)&nbsp;{z&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[T[x].r].l;&nbsp;rrot(z);&nbsp;lrot(z);}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(T[T[T[x].l].l].sz&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;T[T[x].r].sz)&nbsp;{z&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].l;&nbsp;rrot(z);}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(T[T[T[x].l].r].sz&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;T[T[x].r].sz)&nbsp;{z&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[T[x].l].r;&nbsp;lrot(z);&nbsp;rrot(z);}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;maintain(T[z].l,&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">);&nbsp;maintain(T[z].r,&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">);&nbsp;maintain(z,&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">);&nbsp;maintain(z,&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">);<br />}<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;find(</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;_v)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;root;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;v0;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(i)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;v0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].v;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(_v&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;v0)&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;i;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(_v&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;v0)&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].l;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].r;<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />}<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;Find_Kth(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;K)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;root,&nbsp;s0,&nbsp;m0;<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;s0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[T[i].l].sz0;&nbsp;m0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].mul;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(K&nbsp;</span><span style="color: #000000">&lt;=</span><span style="color: #000000">&nbsp;s0)&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].l;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(K&nbsp;</span><span style="color: #000000">&lt;=</span><span style="color: #000000">&nbsp;s0&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;m0)&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;i;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{K&nbsp;</span><span style="color: #000000">-=</span><span style="color: #000000">&nbsp;s0&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;m0;&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].r;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;ins(</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;_v)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">!</span><span style="color: #000000">root)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;T[</span><span style="color: #000000">++</span><span style="color: #000000">N].v&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;_v;&nbsp;T[N].l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;T[N].sz0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].sz&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].mul&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;root&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;N;<br />&nbsp;&nbsp;&nbsp;&nbsp;}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;root,&nbsp;j;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;v0;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;T[i].sz0</span><span style="color: #000000">++</span><span style="color: #000000">;&nbsp;v0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].v;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(_v&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;v0)&nbsp;{T[i].mul</span><span style="color: #000000">++</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">;}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(_v&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;v0)&nbsp;j&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].l;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;j&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].r;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(j)&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;j;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">break</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;T[</span><span style="color: #000000">++</span><span style="color: #000000">N].v&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;_v;&nbsp;T[N].l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;T[N].sz0&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].sz&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[N].mul&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(_v&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;v0)&nbsp;slc(i,&nbsp;N);&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;src(i,&nbsp;N);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(i)&nbsp;{T[i].sz</span><span style="color: #000000">++</span><span style="color: #000000">;&nbsp;maintain(i,&nbsp;_v&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;T[i].v);&nbsp;i&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[i].p;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;del(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(T[x].mul&nbsp;</span><span style="color: #000000">&gt;</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;T[x].mul</span><span style="color: #000000">--</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(x)&nbsp;{T[x].sz0</span><span style="color: #000000">--</span><span style="color: #000000">;&nbsp;x&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].p;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].l,&nbsp;r&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].r,&nbsp;p;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(l&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;r)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;y;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(y&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[l].r)&nbsp;l&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;y;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;T[x].v&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[l].v;&nbsp;T[x].mul&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[l].mul;&nbsp;p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[l].p;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(l&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;T[p].l)&nbsp;slc(p,&nbsp;T[l].l);&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;src(p,&nbsp;T[l].l);<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">&nbsp;(p)&nbsp;{upd(p);&nbsp;p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[p].p;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(x&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;root)&nbsp;T[root&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;r].p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;{p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[x].p;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(x&nbsp;</span><span style="color: #000000">==</span><span style="color: #000000">&nbsp;T[p].l)&nbsp;slc(p,&nbsp;l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;r);&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;src(p,&nbsp;l&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;r);&nbsp;</span><span style="color: #0000ff">while</span><span style="color: #000000">(p)&nbsp;{upd(p);&nbsp;p&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[p].p;}}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />}<br /></span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;</span><span style="color: #0000ff">long</span><span style="color: #000000">&nbsp;h(</span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;x)<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;F[Q[x]]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;a[Q[x&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">]];<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;solve()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;F[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;front&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;rear&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;&nbsp;Q[</span><span style="color: #000000">0</span><span style="color: #000000">]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />&nbsp;&nbsp;&nbsp;&nbsp;re1(i,&nbsp;n)&nbsp;{<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(;&nbsp;front</span><span style="color: #000000">&lt;=</span><span style="color: #000000">rear&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;Q[front]</span><span style="color: #000000">&lt;</span><span style="color: #000000">b[i];)&nbsp;{</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(front&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;rear)&nbsp;del(find(h(front)));&nbsp;front</span><span style="color: #000000">++</span><span style="color: #000000">;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">for</span><span style="color: #000000">&nbsp;(;&nbsp;front</span><span style="color: #000000">&lt;=</span><span style="color: #000000">rear&nbsp;</span><span style="color: #000000">&amp;&amp;</span><span style="color: #000000">&nbsp;a[Q[rear]]</span><span style="color: #000000">&lt;=</span><span style="color: #000000">a[i];)&nbsp;{</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(front&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;rear)&nbsp;del(find(h(rear&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">)));&nbsp;rear</span><span style="color: #000000">--</span><span style="color: #000000">;}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Q[</span><span style="color: #000000">++</span><span style="color: #000000">rear]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;i;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(front&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;rear)&nbsp;ins(h(rear&nbsp;</span><span style="color: #000000">-</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">1</span><span style="color: #000000">));<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(root)&nbsp;F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;T[Find_Kth(</span><span style="color: #000000">1</span><span style="color: #000000">)].v;&nbsp;</span><span style="color: #0000ff">else</span><span style="color: #000000">&nbsp;F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;INF;<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(F[b[i]]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;MAX[i]&nbsp;</span><span style="color: #000000">&lt;</span><span style="color: #000000">&nbsp;F[i])&nbsp;F[i]&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;F[b[i]]&nbsp;</span><span style="color: #000000">+</span><span style="color: #000000">&nbsp;MAX[i];<br />&nbsp;&nbsp;&nbsp;&nbsp;}<br />&nbsp;&nbsp;&nbsp;&nbsp;res&nbsp;</span><span style="color: #000000">=</span><span style="color: #000000">&nbsp;F[n];<br />}<br /></span><span style="color: #0000ff">void</span><span style="color: #000000">&nbsp;pri()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;cout&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;res&nbsp;</span><span style="color: #000000">&lt;&lt;</span><span style="color: #000000">&nbsp;endl;<br />}<br /></span><span style="color: #0000ff">int</span><span style="color: #000000">&nbsp;main()<br />{<br />&nbsp;&nbsp;&nbsp;&nbsp;init();<br />&nbsp;&nbsp;&nbsp;&nbsp;prepare();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">if</span><span style="color: #000000">&nbsp;(</span><span style="color: #000000">!</span><span style="color: #000000">res)&nbsp;solve();<br />&nbsp;&nbsp;&nbsp;&nbsp;pri();<br />&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #0000ff">return</span><span style="color: #000000">&nbsp;</span><span style="color: #000000">0</span><span style="color: #000000">;<br />}<br /></span></div><br /></div><img src ="http://www.cppblog.com/MatoNo1/aggbug/150454.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2011-07-08 12:40 <a href="http://www.cppblog.com/MatoNo1/archive/2011/07/08/150454.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>多重背包问题的单调队列优化</title><link>http://www.cppblog.com/MatoNo1/archive/2011/07/05/150231.html</link><dc:creator>Mato_No1</dc:creator><author>Mato_No1</author><pubDate>Tue, 05 Jul 2011 10:00:00 GMT</pubDate><guid>http://www.cppblog.com/MatoNo1/archive/2011/07/05/150231.html</guid><wfw:comment>http://www.cppblog.com/MatoNo1/comments/150231.html</wfw:comment><comments>http://www.cppblog.com/MatoNo1/archive/2011/07/05/150231.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/MatoNo1/comments/commentRss/150231.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/MatoNo1/services/trackbacks/150231.html</trackback:ping><description><![CDATA[多重背包问题朴素时间复杂度为O(NMS)（这里S是所有物品的数量s之和），经过二进制优化后时间复杂度为O(NMlog2S)，这个复杂度已经能够应付大多数题了，但对于某些特别卡时间的题（比如N*M=10<sup>7</sup>的)，仍然会TLE。这时，可以用单调队列优化，时间复杂度降为O(NM)。<br /><br />首先看一下多重背包问题的朴素转移方程：<br />F[i][j] = max{F[i-1][j-x*w[i]]+x*v[i]} (0&lt;=x&lt;=s[i], j&gt;=x*w[i])<br />如果使用滚动数组，忽略i这一维，设w0=w[i]，v0=v[i]，s0=s[i]，得：<br />F[j] = max{F[j-x*w0]+x*v0} (0&lt;=x&lt;=s0, j&gt;=x*w0)<br />看上去这和单调队列木有神马关系，因为决策下标（j-x*w0）不是一个整数区间，中间是有间隔的。然而可以发现，这个方程的限制条件&#8220;0&lt;=x&lt;=s0，j&gt;=x*w0&#8221;，也就是x的下界是max{0, j/w0（下取整）}，当j单调递增时，这个下界也是单调递增的。这满足单调队列优化的条件中的&#8220;决策下标的下界单调&#8221;&#8230;&#8230;不是，还不能这样说，因为这里的决策下标是j-x*w0，而不是x。<br />那么怎样才可以把决策下标变为x？<br /><br />将决策下标按照模w0的余数进行分类，可以分成w0类，分别对应模w0余0、余1&#8230;&#8230;余(w0-1)的情况。这时，上面方程中的所有决策下标j-x*w0都是同一类的。进一步，设q =j/w0（下取整），r=j%w0，则j=q*w0+r，对于某个决策下标j'，设k=(j'-r)/w0，即j'=k*w0+r。显然可以发现，k的取值范围是：k&gt;=0且q-s0&lt;=k&lt;=q，也即k的下界是max{0, q-s0}&#8212;&#8212;随j的单调而单调。<br />然后，转移方程可以改为（这里把r当成一个已知量了）：<br />F[q*w0+r] = max{F[k*w0+r]+(q-k)*v0} (k&gt;=0且q-s0&lt;=k&lt;=q)<br />即F[q*w0+r]=max{F[k*w0+r]-k*v0}+q*v0 (k&gt;=0且q-s0&lt;=k&lt;=q)<br />设G[k]=F[k*w0+r]得：<br />G[q]=max{G[k]-k*v0}+q*v0 (k&gt;=0且q-s0&lt;=k&lt;=q)<br />这个方程已经可以使用单调队列来优化了！<br /><br />这样可以得出算法：<br />（1）从1到n，枚举i，建立w[i]个空的单调队列，每个队列的元素都是两个int值：(k, val)，表示转换后下标和决策值(G[k]-k*v[i])；<br />（2）从0到m，枚举j，得出q、r的值，对于队列r：<br />【1】删去队首过时（k&lt;q-m[i]）的元素；<br />【2】F[j]入队（这里的F[j]指上一阶段的F[j]，即F[i-1][j]。因此这一步操作一定要先进行），删去队尾所有决策值val不大于(F[j]-q*v[i])的元素。<br />【3】取出队首结点，其val值加上q*v[i]后即为本阶段F[j]的值。<br />最后F[m]即为结果。总时间复杂度为O(NM)。<br /><br />其实这个是可以推广的，即对于如下形式的转移方程（其中H、G和W均为常量，B[i]为决策下标的下界，随i单调）：<br />F[i] = opt{F[i-x*H+W]}+G (B[i]&lt;=i-x*H+W&lt;i，x&#8712;<strong>N</strong>）<br />都可以用上述的办法进行转化，从而进行单调队列优化。<br /> <img src ="http://www.cppblog.com/MatoNo1/aggbug/150231.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/MatoNo1/" target="_blank">Mato_No1</a> 2011-07-05 18:00 <a href="http://www.cppblog.com/MatoNo1/archive/2011/07/05/150231.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>