798. Smallest Rotation with Highest Score
Posted haoweizh
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了798. Smallest Rotation with Highest Score相关的知识,希望对你有一定的参考价值。
Problem:
Given an array A
, we may rotate it by a non-negative integer K
so that the array becomes A[K], A[K+1], A{K+2], ... A[A.length - 1], A[0], A[1], ..., A[K-1]
. Afterward, any entries that are less than or equal to their index are worth 1 point.
For example, if we have [2, 4, 1, 3, 0]
, and we rotate by K = 2
, it becomes [1, 3, 0, 2, 4]
. This is worth 3 points because 1 > 0 [no points], 3 > 1 [no points], 0 <= 2 [one point], 2 <= 3 [one point], 4 <= 4 [one point].
Over all possible rotations, return the rotation index K that corresponds to the highest score we could receive. If there are multiple answers, return the smallest such index K.
Example 1: Input: [2, 3, 1, 4, 0] Output: 3 Explanation: Scores for each K are listed below: K = 0, A = [2,3,1,4,0], score 2 K = 1, A = [3,1,4,0,2], score 3 K = 2, A = [1,4,0,2,3], score 3 K = 3, A = [4,0,2,3,1], score 4 K = 4, A = [0,2,3,1,4], score 3
So we should choose K = 3, which has the highest score.
Example 2: Input: [1, 3, 0, 2, 4] Output: 0 Explanation: A will always have 3 points no matter how it shifts. So we will choose the smallest K, which is 0.
Note:
A
will have length at most20000
.A[i]
will be in the range[0, A.length]
.
Solution:
这道题其实没什么特别的算法,主要还是找规律与优化,暴力解法时间复杂度为O(n2),就是直接模拟题目解释,肯定是效率不够的,代码如下
1 class Solution { 2 public: 3 int bestRotation(vector<int>& A) { 4 int result = 0; 5 int maxScore = 0; 6 for(int k = 0;k != A.size();++k){ 7 int count = 0; 8 for(int i = 0;i != A.size();++i){ 9 if(A[i] <= (i+A.size()-k)%A.size()) 10 count++; 11 } 12 if(count > maxScore){ 13 maxScore = count; 14 result = k; 15 } 16 } 17 return result; 18 } 19 };
现在来思考下线性时间复杂度的解法。通过观察规律可知,对于每个元素A[i],都有一个集合k使得对于k中的每个元素ki,当A旋转ki后A[i]都满足条件,以Example1为例,对于[2, 3, 1, 4, 0],我们得到[1,4),[2,4),[0,2)||[3,5),[4,5),[0,5),解释一下这是什么意思,比如说A[0]=2,当k取[1,4)中的任意值,2这个值和其对应转移后的位置满足条件,score加一。所以我们现在把问题抽象为当k取什么值的时候,满足条件的区间个数最多。这个问题是不是很眼熟?它和Leetcode 732 My Calendar III的解法完全一样,用一个哈希表轻松解决。考虑到题目特殊性,可以用数组代替哈希表,效率会提高不少。
Code:
1 class Solution { 2 public: 3 int bestRotation(vector<int>& A) { 4 vector<int> m(A.size()+1,0); //Or unordered_map<int,int> m; 5 int result = 0; 6 int maxScore = 0; 7 int score = 0; 8 for(int i = 0;i != A.size();++i){ 9 if(i >= A[i]){ 10 m[0]++; 11 m[i-A[i]+1]--; 12 m[i+1]++; 13 m[A.size()]--; 14 } 15 else{ 16 m[i+1]++; 17 m[i+A.size()-A[i]+1]--; 18 } 19 } 20 for(int i = 0;i != A.size();++i){ 21 score += m[i]; 22 if(score > maxScore){ 23 maxScore = score; 24 result = i; 25 } 26 } 27 return result; 28 } 29 };
以上是关于798. Smallest Rotation with Highest Score的主要内容,如果未能解决你的问题,请参考以下文章