在这里做个简单的题解。
zju1021.The Willy Memorial Program
http://www.shaidaima.com/source/view/11171
管数目不多,管的长度也不多,那么总的蓄水量也很少,因此可以直接模拟滴水的过程,就是一秒一个单位的水然后判断水是否溢出或者到达目标状态,水的高度可以是小数,但是我用整数来处理然后必要时在进行特殊判断。
zju1030.Farmland
http://www.shaidaima.com/source/view/11172
把平面图每个平面提取出来再判断是否简单。遍历每个平面的方法是每次选一条没有遍历过的边(不同方向示为不同)作为新平面的第一条边,然后以这表边反方向后顺时针的下一条边作为第二条边,然后以第二条表边反方向后顺时针的下一条边作为第三条边,以此类推,最后回到第一条边后结束,然后同时求出有符号面积,如果是负的就是外表面,在这里肯定不用考虑,剩下都可能是答案,然后用set的也好,判一下点是否重复就可以判断出是否简单。
zju1041.Transmitters
http://www.shaidaima.com/source/view/11173
比zju1030更简单的平面几何题,容易想到肯定会有一个点落在直径上,所以枚举落在直径上的点,然后就可确定两个不同的半圆,然后再分别暴力枚举一遍看哪些点落在半圆内同时更新答案。
zju1043.Split Windows
http://www.shaidaima.com/source/view/11174
给出的是后缀表达式,直接从左到右扫一次模拟一下边长即可
zju1060.Sorting It All Out
http://www.shaidaima.com/source/view/11175
枚举要判断的表达式数,再用拓补排序来判断表达式组无解,唯一解还是多解。
zju1063.Space Station Shielding
http://www.shaidaima.com/source/view/11176
三维矩形上floodfill看那些面没有被覆盖而且能通过没被占据的方格被外表面所看到……这些面的数目就是答案。
zju1066.Square Ice
http://www.shaidaima.com/source/view/11177
不是0的直接就可以知道方向,0的那些从上到下,从左到右枚举,如果上面没被覆盖,就选择上面放一个'H',否则选择下面,左右同理。
zju1100.Mondriaan's Dream
http://www.shaidaima.com/source/view/11178
然后用dfs来求出转移矩阵。即c[xx...xb][yy...yb](yy...yb与xx...xb表达的意思相同)表示能否同xx...xb经过添加一个单位使得变成yy...yb,因此dp[i+1][xx...xb]=sigma{dp[i][yy...yb]*c[yy...yb][xx...xb] | 00...0b<=xx...xb<=11...1b} 时间复杂度是R*(2^C)^2,如果当R很大,C很小的是否可以用矩阵乘法优化到log(R)*(2^C)^3
zju1103.Hike on a Graph
http://www.shaidaima.com/source/view/11179
状态很少,直接bfs
zju1116.A Well-Formed Problem
http://www.shaidaima.com/source/view/11180
比较麻烦的字符串处理,首先划分出tag类,可以封装到一个类里,然后用一个函数判断是否合法……然后用栈来模拟判断整个文本是否合法。感觉数据还是比较厚道,按照他给出的规则判断就可以了……
zju1123.Triangle Encapsulation
http://www.shaidaima.com/source/view/11181
Program 4 by team X
End of program 4 by team X这两句话是放在一头一尾的
zju1138.Symbolic Derivation
http://www.shaidaima.com/source/view/11182
每次找出最后一个运算的符号,然后变成两个子问题递归下去然后根据给出的rule合并,括号不能忽略,注意有可能两个符号连在一起要合并成一个符号,如1+-2就换成1-2。
zju1144.Robbery
http://www.shaidaima.com/source/view/11183
bfs得出某一天在某些位置是否有可能,然后如果存在一天只有一处地方则输出。
zju1145.Dreisam Equations
http://www.shaidaima.com/source/view/11184
状态不多,直接搜索所有情况
zju1155.Triangle War
http://www.shaidaima.com/source/view/11186
总的边数就18条,于是可以用dp[w][xx...xb]表示谁做先手,边的选择情况,然后先手得到的最高分……状态转移就有点像模拟这个游戏
因为那个图形是凸的,显然每一切都会顺着其中的一条边,因为边数/点数很小,于是枚举所有切的顺序,然后每一次可以根据前面来判断这一次需要切多长,最后总和取最小的那一次。
比较简单的平面几个,直接暴力模拟,光的反射跟镜面反射一样,然后那个镜面就是光线与圆的第一个交点和与那个圆的圆心形成的直线的垂线,而且还要是那个圆的切线那一条。求反射根据角度判断也行,镜面反射原理也行。就是基于反射角等于入射角。
就是判断一个二分图的其中一些匹配是一定的,方法就是先随便生成一个匹配,然后枚举去掉一条在匹配上的边,如果还是能匹配成功,则说明这个匹配不是固定的,否则就是。重新匹配过后要还原,不然会有问题。
认真读清楚游戏的rule,然后那些概率的转移倒不是太难。
bfs,用RK hash记录状态。
枚举顶点和高度,要分奇偶……用求和的方式就可以比较快求出连续一片是否全白。
}
先用dijkstra求出每个点到1号点的最短路,然后枚举每一个点和每一条边的出最后结束的点和时间,注意在边上的点不一定是中点。
zju1301.The New Villa
http://www.shaidaima.com/source/view/11164
按所在房间号和灯的开关情况编码,然后bfs,相同编码就是相同状态。
zju1321.Parallelepiped Walk
http://www.shaidaima.com/source/view/11166
为了方便可以先把一个点固定到一面,然后以那个面为base不动。
zju1387.Decoding Morse Sequences
http://www.shaidaima.com/source/view/11167
把morse转成字符串是多解的,但是把字符串转成morse就是唯一了,所以把答案转成morse,建一个trie图,然后在上面dp……
zju1389.Fill the Cisterns!
http://www.shaidaima.com/source/view/11168
二分答案。
zju1391.Horizontally Visible Segments
http://www.shaidaima.com/source/view/11169
大体思路是线段按x轴排序,按x从小到大枚举相连的第二条和第三条线段,然后求出有多少条可以做第1条线段。
这样做时间复杂度比较大,于是想一个优化的方案,枚举第二条线段的时候暴力染色,然后扫一次y轴就可以知道x轴比第二条线段小的与第二条相连的第一条线段有哪些,用bool数组记录。然后枚举第三条的时候也是扫一次y轴,但是这样还是N^3,但是我们枚举第三条的时候发现因为从x轴小到大枚举,如果以前的枚举覆盖了一定范围,那么后面的线段就可以不枚举这个范围的点,具体做法是用一个next数组记录下一个没被记录的点,动态更新,那么可以证明点的访问数与N是线性相关的。时间复杂度是O(N^2)的,勉强可以过。
zju1413.2D Nim
http://www.shaidaima.com/source/view/11170
如果两个图形相等,就可连一条边,最后的一个二部图,用匈牙利跑一下看是否能完全匹配。
判断两个图形是否相等:固定一个点,通常是最左最上点,然后其他点用相对距离,然后排序,注意旋转的时候最左最上点可能会改变,而且相对距离可要重新排序。然后用这些相对距离判断是否全相等来判断两个图形是否相等。
zju1423.(Your)((Term)((Project)))
外面是'-'而且里面有操作符就把这个括号删掉,注意表达式内有空格
zju1425.Crossed Matchings
首先预处理出一个数组first[i][j], 表示第二层数第i个位置后第一个j出现的位置,然后dp[i][j]表示上一层取到i,下一层取到j的最优解。
那么dp[i][j] ==> dp[i+1][j], //i+1这个点不选;
同时dp[i][j] ==> dp[k][first[first[j][num[k]]][num[i+1]]//i+2<=k<=n,first[j][num[k]]与first[first[j][num[k]][num[i+1]]存在,意思就是相交的两个数分别在第一层i+1和k的位置出现。然后下面一层我们肯定要最出现早最优,因为这样后面才有更多的位置,因此一个就是出现在j后的第一个num[k], 第二个出现在first[first[j][num[k]]][num[i+1]]。
zju1426.Counting Rectangles
枚举矩形的两根竖的线段,扫描一次求出多少条横的线段同时穿过这两条线段,那么任意两天横的都可以和这条竖的组成矩形,所以假如有h条,则答案+=C(h,2);
zju1448.Pattern Matching Using Regular Expression
枚举被匹配字串的开始处,然后dp[i][j]表示到模式的第i个单元,字符串的第j位是否可行,这个dp就比较简单。
然后建议把模式传分成一个个小单元出来,表明好类型,是否带*,(x+可以换成xx*的形式),然后模式串按单元划分而不是按字符,这样应该好做一些。然后我遇到一个比较蛋疼的trick是[c1-c2]中c1和c2是']'。
zju1460.The Partition of a Cake
面数+点数-边数=2,所以求出点数和边数就行,这样个问题都可以归到求两条线段的交点问题,这个问题直接解方程。
zju1462. Team Them Up!
用给出的图求补图就是表示两个点是否要分在不同边,那么如果不是二部图,即存在奇环,无解,否则分成二部图之后dp[i][j], 表示一块含有i个点,一块含有j个点是否有可能。
zju1463.Brackets Sequence
dp[i][j],表示i到j这部分的括号最小要添加的括号数,然后dp[i][j]=min{dp[i][k]+dp[k+1][j] | i<=k zju1504.Slots of Fun 用了一个觉得很cheat的算法,因为最多只有不超过100的圆,而且圆的位置是固定的,所以先预处理出每一个圆的笛卡尔坐标,接着枚举三个相同字符的圆然后看两两相对距离是否相等。 zju1506.Left labyrinths 这道题一直看不懂,最后问了人才发现走的优先顺序是向左,向后,向右,向前…… 求门口的位置,你可以首先从迷宫最左最上的点的左边一点开始走,用一个标记记录里外,一开始为外,按照同样的优先顺序,当走到一个#.#(可以竖着)的时候标记为里,如果再走回这个点就标记为外。然后一个2*2的全是点阵的方格就是courtyard. 最后用方位和方向来做判重做bfs。 zju1509.Family 在一个拓补图上面dp,dp[y][x]=dp[x][y]=(dp[x][pa[y][0]]+dp[x][pa[y][1]])/2, 要求x在拓补序中先于y,然后pa[y][0]和pa[y][1]分别是y的两个parent。 输出略坑,要用到Java的BigDecimal…… zju1509.This Sentence is False 构一个图,用dfs判断一个连通块是否有冲突,并且把一个连通块按对错分成两部分,把大的那一部分加进答案。