该问题要求模拟一系列“玩家1对1对战”的过程,每轮选择当前生命值最小且不为0的两名玩家进行PK,直到无法匹配出两名玩家或所有玩家生命值归零。
显然,每轮都要快速地找到当前生命值最小的两名玩家,因此可以使用 优先队列(最小堆) 来维护玩家集合。
(life, id)
为键插入最小堆。有一款游戏,里面有N个游戏玩家 (1<=N<100000),每个玩家都有一个初始的生命能量值lifePower(0<=lifePower<=231−1)
游戏规则:经过多玩家1对1 PK 直到游戏结束,每一轮PK都是从游戏中尚存的所有玩家中挑选生命能量值最小且不为0的2个玩家进行PK(如果在挑选符合PK条件的2个玩家过程中,能量值相同的候选玩家有多个时,则挑选玩家编号小的玩家参与PK),如是两个玩家的生命能量值相同,则2个玩家同归于尽,生命能量值都归为0,PK后都退出游戏;如果2个玩家的生命能量值不同,则能量值大的玩家胜出,PK过程胜出玩家会消耗掉另一个玩家的同等数量的生命能量值,但是PK胜出后,则剩余生命能量值会膨胀3倍(最大不超过32位有符号整数的最大值即 231−1),即为该玩家最终的生命能量值为剩余生分能量值的3倍。PK胜出的玩家仍可继续游戏;
如果游戏无法挑选出2个符合条件的玩家进行PK时,游戏结束;
请设计一个高效的算法,让游戏按规则进行玩家PK,直到游戏结束。
第一行为游戏玩家的数量,取值范围:1<=N<100000
第二行为空格间隔的 N 个游戏玩家的生命能量值 lifePower,按照玩家编号从1到N排列。取值范围:0<=lifePower<231−1
打印最后PK胜出玩家的编号和该玩家的最终生命能量值,以1个空格为间隔。如果游戏经过PK后,没有留存下来生命能量值大于0的玩家,则打印−1。
输入
4
2 5 1 8
输出
4 6
说明
第1轮PK,最小的2个玩家是玩家1和玩家3,生命能力值分别是2和1,玩家1胜出,剩余能量值为1,膨胀3倍后最终生命能量值为3
第1轮PK后所有玩家的生命能量值为:3 5 0 8
第2轮PK,最小的2个玩家是玩家1和玩家2,生命能力值分别是3和5,玩家2胜出,剩余能量值为2,膨胀3倍后最终生命能量值为6
第2轮PK后所有玩家的生命能量值为:0 6 0 8
第3轮PK,最小的2个玩家是玩家2和玩家4(也是最后2个玩家),生命能量值分别是6和8,玩家4胜出,剩余能量值为2,膨胀3倍后最终生命能量值为6
第3轮PK后所有玩家的生命能量值为:0 0 0 6
返回 4 6
输入
3
2 5 9
输出
-1
说明
第1轮PK,最小的2个玩家是玩家1和玩家2,生命能力值分别是2和5,玩家2胜出,剩余能量值为3,膨胀3倍后最终生命能量值为9
第1轮PK后所有玩家的生命能量值为:0 9 9
第2轮PK,最小的2个玩家是玩家2和玩家3,生命能力值分别是9和9,同归于尽,最后游戏没有剩余玩家,返回−1