Program to Find Out the Maximum Final Power of a List in Python


Suppose, we have a list and the power of a list is defined by the sum of (index + 1) * value_at_index over all indices. Alternatively, we can represent it like this −

$$\displaystyle\sum\limits_{i=0}^{n-1} (i+1)\times list[i]$$

Now, we have a list nums that has N positive integers. We can select any singular value in the list, and move (not swap) it to any position, it can be shifted to the beginning of the list, or to the end. We can also choose to not move any position at all. We have to find the maximum possible final power of the list. The result has to be modded by 10^9 + 7.

So, if the input is like nums = [4, 2, 1], then the output will be 16.

To solve this, we will follow these steps −

  • P := [0]

  • base := 0

  • for each i, x in index i and item x in A, 1, do

    • insert P[-1] + x at the end of P

    • base := base + i * x

  • Define a function eval_at() . This will take j, x

    • return -j * x + P[j]

  • Define a function intersection() . This will take j1, j2

    • return(P[j2] - P[j1]) /(j2 - j1)

  • hull := [-1]

  • indexes := [0]

  • for j in range 1 to size of P, do

    • while hull and intersection(indexes[-1], j) <= hull[-1], do

      • delete last element from hull

      • delete last element from indexes

    • insert intersection(indexes[-1], j) at the end of hull

    • insert j at the end of indexes

  • ans := base

  • for each i, x in index i and item x in A, do

    • j := the portion where x can be inserted in hull, maintaining the sorted order

    • j := maximum of j - 1, 0

    • ans := maximum of ans, base + eval_at(i, x) - eval_at(indexes[j], x)

  • return ans mod (10^9 + 7)

Example 

Let us see the following implementation to get better understanding −

 Live Demo

import bisect
class Solution:
   def solve(self, A):
      P = [0]
      base = 0
      for i, x in enumerate(A, 1):
         P.append(P[-1] + x)
         base += i * x
      def eval_at(j, x):
         return -j * x + P[j]
      def intersection(j1, j2):
         return (P[j2] - P[j1]) / (j2 - j1)
      hull = [-1]
      indexes = [0]
      for j in range(1, len(P)):
         while hull and intersection(indexes[-1], j) <= hull[-1]:
            hull.pop()
            indexes.pop()
         hull.append(intersection(indexes[-1], j))
         indexes.append(j)
      ans = base
      for i, x in enumerate(A):
         j = bisect.bisect(hull, x)
         j = max(j - 1, 0)
         ans = max(ans, base + eval_at(i, x) - eval_at(indexes[j], x))
      return ans % (10 ** 9 + 7)

ob = Solution()
print (ob.solve([4, 2, 1]))

Input

[4, 2, 1]

Output

16

Updated on: 23-Dec-2020

144 Views

Kickstart Your Career

Get certified by completing the course

Get Started
Advertisements