There are several cards arranged in a row, and each card has an associated number of points. The points are given in the integer array cardPoints.

In one step, you can take one card from the beginning or from the end of the row. You have to take exactly k cards.

Your score is the sum of the points of the cards you have taken.

Given the integer array cardPoints and the integer k, return the maximum score you can obtain.

&nbsp;
Example 1:

Input: cardPoints = [1,2,3,4,5,6,1], k = 3
Output: 12
Explanation: After the first step, your score will always be 1. However, choosing the rightmost card first will maximize your total score. The optimal strategy is to take the three cards on the right, giving a final score of 1 + 6 + 5 = 12.


Example 2:

Input: cardPoints = [2,2,2], k = 2
Output: 4
Explanation: Regardless of which two cards you take, your score will always be 4.


Example 3:

Input: cardPoints = [9,7,7,9,7,7,9], k = 7
Output: 55
Explanation: You have to take all the cards. Your score is the sum of points of all cards.


&nbsp;
Constraints:


	1 &lt;= cardPoints.length &lt;= 105
	1 &lt;= cardPoints[i] &lt;= 104
	1 &lt;= k &lt;= cardPoints.length


class Solution:
    def maxScore(self, cardPoints: List[int], k: int) -> int:
        total_cards = len(cardPoints)
        total = sum(cardPoints)
        window_size = total_cards - k
        window_total = 0

        if total_cards == k:
            return total

        for i in range(total_cards - k):
            window_total += cardPoints[i]
        max_diff = total - window_total
        for i in range((total_cards - k), total_cards):
            window_total += cardPoints[i]
            window_total -= cardPoints[i-window_size]
            if total - window_total > max_diff:
                max_diff = total - window_total
        return max_diff
class Solution {
    public int maxScore(int[] cardPoints, int k) {
        int n = cardPoints.length;
        int[] totalSum = new int[n];
        int sum = 0;
        for(int i=0;i<n;i++){
            sum += cardPoints[i];
            totalSum[i] = sum;
        }
        if(n==k){
            return sum;
        }
        int score =0;
        for(int i=0;i<=k;i++){
            int j = i+n-k-1;
            int subsum = 0;
            if(i==0){
                subsum = totalSum[j];
            }
            else{
                subsum = totalSum[j]-totalSum[i-1];
            }

            score = Math.max(score,sum-subsum);
        }
        return score;
    }
}
class Solution {
public:
    int maxScore(vector<int>& cardPoints, int k) {

        int max_s = 0, left =0, right = 0, n = cardPoints.size();

        //getting sum of k right elements
        for(int i = 0; i<k; i++){
            right += cardPoints[n-i-1];
        }

        // Assumming max as sum of k right elements
        max_s = right;
        for(int i = 0; i<k; i++){
            left += cardPoints[i];
            right -= cardPoints[n-k+i];
            max_s = max(max_s, left+right);
        }
        return max_s;
    }
};
/**
 * @param {number[]} cardPoints
 * @param {number} k
 * @return {number}
 */

// Obtaining k cards from the beginning or end of the row for the largest sum, meaning leaving the
// array with n-k adjacent cards with the min sum
// therefore, this transform the problem to finding the minSum of subarray of length n-k
// we use slide window to calculate the minSubArraySum
var maxScore = function(cardPoints, k) {
    const n = cardPoints.length, d = n-k // d is the window length
    let sum = 0
    for (let i = 0; i < d; i++) {
        sum += cardPoints[i]
    }
    let minWindowSum = sum, totalSum = sum
    console.log(sum)
    for (let i = d; i < n; i++) {
        // the sum of the next window will the the sum of previous window + the next card (the end card of the next window) - the beginning card of the previous window
        sum += cardPoints[i] - cardPoints[i-d]
        minWindowSum = Math.min(minWindowSum, sum)
        totalSum += cardPoints[i]
    }
    // the ans will be the sum of all cards - the sum of min subArray
    return totalSum - minWindowSum
};
Maximum Points You Can Obtain from Cards