2014嘉杰信息杯ACM/ICPC湖南程序设计邀请赛暨第六届湘潭市程序设计竞赛 解题报告

来源:互联网 发布:阿里云 腾讯云 aws 编辑:程序博客网 时间:2024/05/03 00:39

A simple problem

题目大意:求n % 1 + n % 2 + ... + n % n(n≤10^12)。

分析:别被题目名字骗了,这题不算难,但绝对算坑爹。先分析n % k怎么求,从后往前
n % k = n - k, k ∈ [n / 2 + 1, n]
n % k = n - 2k, k ∈ [n / 3 + 1, n / 2]
...
一直照这样求到n / sqrt(n)就行了,剩下的一个循环就好了,时间复杂度O(sqrt(n)),也就是10^6级。坑爹的来了,答案太大,long long也存不下,自己写下大整数吧。因为可以肯定结果不超过10^27,所以我的大整数直接用3个long long表示。代码中的一大半都在写大整数。。。。

Path


Range

题目大意:给定一个数列,求出所有子区间的范围(最大值 - 最小值 + 1)之和。

分析:当然不是一个区间一个区间地算,而是把问题分解为(最大值的和) - (最小值的和) + (区间总数 = n(n + 1) / 2)。以最大值之和为例,需要求出以每个a[i]为最大值的区间数目,可以用单调栈,也可以用DP,两者是一样的(参见另一篇文章),求出从位置i开始向左和向右延伸的最大长度。若以a[i]为最大值的最大区间为[left, right],那么以a[i]为最大值的区间总数为(i - left + 1) * (right - i + 1),即在位置i左右(含i)各取一个数。
需要处理的另一个问题是相同数字。比如序列1 2 1,以两个1为最小值的区间都是[1, 3](下标从1开始),算第一个1时,算到的区间有[1, 1], [1, 2], [1, 3],算第二个1时,算到的区间有[1, 3], [2, 3], [3, 3],也就是说,区间[1, 3]被算了两次。其实算第二个1时应该把最大区间[1, 3]换为[2, 3],2是怎么来的呢?就是上一个1的后一个位置,因为上一个1把端点在它左右的区间全部计算过了,现在只需计算左右端点都在它右边的区间。所以计算前先判断,如果最大区间[left, right]包含了上一个相同数字的位置,就把left换为上一个位置 + 1。这一点确实比较坑爹。

Dormitory's Elevator

题目大意:有一群人要上楼,但电梯不能在相邻楼层停靠,上下一层楼分别消耗能量a, b,问最少消耗的能量。

分析:明显的动态规划,但是考虑到当前状态要受未来状态的影响(假设当前楼层不停,那么到该楼层的人可以选择提前下电梯,也可以选择坐到楼上再走下来,而这与下一层的停靠情况相关),就要把未来的情况考虑进去。用dp[i][0]表示在i层停,dp[i][1]表示在i和i + 1都不停(那么i - 1和i + 2一定都停,因为不可能连续3层都不停),dp[i][2]表示i不停但i - 1和i + 1都停,dp[i][3]表示i - 1和i都不停,总共只有这4种情况。关系很简单,就不说了,关键是这种把未来的影响转移到当前状态的思想。

Welcome to XTCPC

分析:简单题。

Skill Tree

题目大意:从一个倒三角里面选取m个数使得其和最大,要求是第一行可任意选取,其余各行在选取之前必须把上一行左上角和右上角两个数都选取。

分析:很经典的斜对角DP,和打砖块一模一样(HNOI 2004 打砖块,去网上搜一下吧,可以找到一份PPT,讲得很详细),关键是图的转换。

Alice and Bob

分析:水题。

Happy Number

分析:很简单,打表就行。

Intervals


Mosquitoes


0 0
原创粉丝点击