一模 (1) day2
第一题:(水题)
题目大意:就是给出扫雷的图,然后统计每个九宫格的雷的个数。
解题过程:
1.好久没做这样的水题了。直接模拟水过。。
第二题:
题目大意:给出一个长度小于1000的数k,要求一个尽可能小的数x,这个数的各个位的乘积为k;
解题过程:
1.想不到什么高级的算法,感觉就是考高精度除法,于是果断dfs爆搜,既然要求尽可能小的数,那么每次就从9到2一个一个试除,第一个找到的答案就是最后答案。这样20个点能过17个。
2.对比了标程,发现有2个剪枝:
首先如果上一次除的是 x,那么这一次 不必从9开始试除,因为比x大的因此 在之前肯定已经除掉了。
其次,如果当先枚举到能被x除尽,那么不必枚举比x小的那些数来除,因为这样也必定不比除x优。证明:假设 x能除尽当前的数,且存在y<x 能除尽当前的数,且之后能找到答案, 那么 除掉y之后,再去除的必定是x。 但是这样还不如 先除x在除y。而如果先除x找不到答案,那么先除y也一样找不到答案。
3.还是一道非常不错的题目,结合了贪心,搜索剪枝和高精度。从这题可以感受到,有的时候真的一个小小的优化可以让你的程序跑得快许多。
第三题:
题目大意:给出N个点M条边的无向图,要求一条从s到t的路径,使得 路径上 权值最大边的权值 除以 权值最小边的权值 的商最小, 结果输出这个商,如果是分数,用X/Y的形式表示,X和Y互质; N<=500,M<=5000
解题过程:
1.一开始想到的自然是 给边按权值排序,枚举最小值,二分最大值,用并查集判断联通,但是目测会超时。
2.然后就改成spfa:做两次spfa,分别从s,t出发 求出到每一个点的路径权值最大边的最小值,权值最小边的最大值,最后枚举中间点。结果 发现样例过不去,仔细想了想 其实这样的贪心是不对的。因为没法保证最大边最小和最小边最大 在同一条路径上。
3.看时间不够了,还是老老实实按1的方法来写,2个点超时。 看了下标程,发现有一个剪枝:就是如果枚举最小值的时候,上一个最小值和当前的相等,那么直接跳过。 加上这个减枝竟然神奇的0ms过了。。 而且标程的最大边没有二分,也是枚举的。时间复杂度O(M*(M+N*α(N))),按理说应该超时的。常数小,反而0ms。 我一开始的程序复杂度是大致 O(M*logM*M),确实慢了。 二分完全没有必要。