813最大平均值和的分组

题目:我们将给定的数组 A 分成 K 个相邻的非空子数组 ,我们的分数由每个子数组内的平均值的总和构成。计算我们所能得到的最大分数是多少。注意我们必须使用 A 数组中的每一个数进行分组,并且分数不一定需要是整数。

来源:https://leetcode-cn.com/problems/largest-sum-of-averages/

法一:自己的代码

思路:动态规划,要先正确的定义dp数组,dp[i][j]表示对0到j的i次分组的最大值.这个问题要精确控制j的范围,会大大缩短时间.

from typing import List
class Solution:
    def largestSumOfAverages(self, A: List[int], K: int) -> float:
        size = len(A)
        dp = [[0] * size for i in range(K)]
        dp[0][0] = A[0]
        for i in range(1,size):
            # 注意第一行只需直接求和再求平均,
            dp[0][i] = sum(A[0:i+1])/(i+1)
        for i in range(1,K):
            for j in range(i,size):
                print('kkk',j)
                dp[i][j] = max( dp[i-1][x] + sum(A[x+1:j+1])/(j-x) for x in range(j))
        print(dp)
        return dp[-1][-1]
View Code

改进后:

from typing import List
class Solution:
    def largestSumOfAverages(self, A: List[int], K: int) -> float:
        size = len(A)
        dp = [[0] * size for i in range(K)]
        for i in range(size):
            # 注意第一行只需直接求和再求平均,
            dp[0][i] = sum(A[:i+1])/(i+1)
        # 求和,后面任意长度求和只需相减即可
        for i in range(size)[::-1]:
            A[i] = sum(A[0:i+1])
        for i in range(1,K):
            # 这里的两个范围会大大缩短时间,之所以从i开始是因为第i次分组的时候,至少要有i个元素
            # size-K+i+1 = size-(K-(i+1)) 第i次分组的时候,最后的几个是无效的,
            # 比如K为5,即分五组,则分第3组的时候,只需到倒数第3个几个,因为要保证最后要分成5组
            for j in range(i,size-K+i+1):
                # 这里是动态规划的关键,第i次分割的最大值,
                # 等于第i-1次从0到x的最大值加上x到j的和的平均值 的最大值
                dp[i][j] = max( dp[i-1][x] + (A[j]-A[x])/(j-x) for x in range(j))
        return dp[-1][-1]
if __name__ == '__main__':
    duixiang = Solution()
    a = duixiang.largestSumOfAverages(A=[9,1,2,3,9,4,5], K=4)
    print(a)
View Code

ttt

 

posted on 2020-01-31 15:55  吃我一枪  阅读(253)  评论(0编辑  收藏  举报

导航