<|instruction|>
Solve the below problem. The solution should start with an abridged problem statement. Then key observations. Then full solution based on the observations. Then C++ and Python implementations with comments.

183. Painting the balls
time limit per test: 0.25 sec.
memory limit per test: 4096 KB
input: standard input
output: standard output



Petya puts the N white balls in a line and now he wants to paint some of them in black, so that at least two black balls could be found among any M successive balls. Petya knows that he needs Ci milliliters of dye exactly to paint the i-th ball. Your task is to find out for Petya the minimum amount of dye he will need to paint the balls.

Input
The first line contains two integer numbers N and M (2<=N<=10000, 2<=M<=100, M<=N). The second line contains N integer numbers C1, C2, ..., CN (1<=Ci<=10000).

Output
Output only one integer number - the minimum amount of dye Petya will need (in milliliters).

Sample test(s)

Input
6 3
1 5 6 2 1 3

Output
9

Note
Example note: 1, 2, 4, 5 balls must be painted.
Author:	Andrew V. Lazarev
Resource:	ACM International Collegiate Programming Contest 2003-2004
North-Eastern European Region, Southern Subregion
Date:	2003 October, 9

<|response|>
1. Abridged problem statement  
We have N white balls in a row, each ball i can be painted black at cost Ci. We must paint enough balls so that in every contiguous block of M balls there are at least two black balls. Compute the minimum total cost.

2. Key observations  
- If you look at any two consecutive painted balls, say at positions p and q, then any window of length M that starts between p+1 and q must still contain both p and q (or p and one before, or q and one after). To guarantee two blacks in every M-segment, the gap (q–p) between adjacent painted balls must be ≤M.  
- We can also treat the “start” as having an imaginary painted ball at position 0, and the “end” as having an imaginary painted ball at position N+1, to enforce the first and last window constraints. In practice, we only need to check that the first real painted ball is close enough to the left end, and the last real painted ball is close enough to the right end.  
- A dynamic programming on the last painted ball index and the gap back to the previous painted ball captures the needed “two-per-M” constraint locally.

3. Full solution approach  
Define dp[i][d] = minimum cost to paint ball i black as the k-th painted ball, with the distance back to the previous painted ball equal to d (that is, if the previous painted ball was at position i–d).  
- We only allow 1 ≤ d ≤ M, because if d > M, some M-segment between those two painted balls would contain at most one black.  
- Initialization (first painted ball): we imagine a “virtual” painted ball at position 0. If we choose to paint ball i first, then its gap to the virtual one is d = i – 0 = i. To ensure the first actual window of length M (positions 1..M) sees two blacks, we need i < M. For every i with 1 ≤ i < M, set dp[i][i] = Ci.  
- Transition: from a state (i, d1), we can paint a new ball j > i. Let the gap dist = j – i (1 ≤ dist ≤ M). We require d1 + dist ≤ M, so that any window spanning the two painted balls at i and j still has at least two blacks. Then we update  
    dp[j][dist] = min(dp[j][dist], dp[i][d1] + Cj).  
- Answer: among all states (i, d) such that the gap from ball i to the end (N+1) plus d is ≤ M (i.e., (N+1–i) + d ≤ M+1, or equivalently N–i + d ≤ M), take the minimum dp[i][d]. That ensures the trailing segment also has two blacks.  
- Complexity: there are O(N·M) states, and each state considers up to M transitions, so O(N·M²). With M ≤ 100 and N ≤ 10000 this is acceptable in optimized C++. We can optimize the “inner” transition by keeping a prefix minimum of dp[i][*] to reduce one factor of M, but the straightforward O(N·M²) also fits under 0.25 s in C++.

4. C++ implementation with detailed comments  
```cpp
#include <bits/stdc++.h>
using namespace std;
static const int INF = 1e9;

int main() {
    ios::sync_with_stdio(false);
    cin.tie(nullptr);

    int N, M;
    cin >> N >> M;
    vector<int> C(N+1);
    for(int i = 1; i <= N; i++) {
        cin >> C[i];
    }

    // dp[i][d]: minimum cost if we paint ball i (1-based) black,
    // and the previous painted ball was at i-d. We require 1 ≤ d ≤ M.
    // We'll use 1..N for balls, ignore index 0 in dp.
    vector<vector<int>> dp(N+1, vector<int>(M+1, INF));

    // Initialize: paint the first real black ball at i, gap to "virtual" at 0 is d=i.
    // We need i < M so that the first segment [1..M] has at least two blacks
    // (the virtual at position 0 and this one at i).
    for(int i = 1; i < M && i <= N; i++) {
        dp[i][i] = C[i];
    }

    int answer = INF;

    // Process each painted state
    for(int i = 1; i <= N; i++) {
        // Check if we can finish after painting at i:
        // the gap from i to N+1 is (N+1 - i). We require d + (N+1-i) ≤ M+1,
        // i.e. d + (N - i) ≤ M.
        for(int d = 1; d <= M; d++) {
            int cost = dp[i][d];
            if(cost >= INF) continue;
            if(d + (N - i) <= M) {
                answer = min(answer, cost);
            }
        }

        // Try to paint the next ball at j = i + dist
        for(int d1 = 1; d1 <= M; d1++) {
            int baseCost = dp[i][d1];
            if(baseCost >= INF) continue;
            // dist is gap to next painted ball
            for(int dist = 1; dist <= M; dist++) {
                int j = i + dist;
                if(j > N) break;          // beyond end
                if(d1 + dist > M) break;  // would violate two-per-M
                int newCost = baseCost + C[j];
                if(newCost < dp[j][dist]) {
                    dp[j][dist] = newCost;
                }
            }
        }
    }

    cout << answer << "\n";
    return 0;
}
```

5. Python implementation with detailed comments  
```python
import sys
input = sys.stdin.readline
INF = 10**18

def main():
    N, M = map(int, input().split())
    C = [0] + list(map(int, input().split()))  # 1-based

    # dp[i][d]: minimum cost if ball i is painted, and previous painted was at i-d (1 ≤ d ≤ M)
    dp = [ [INF]*(M+1) for _ in range(N+1) ]

    # Initialize first painted ball at i, gap = i to virtual 0; require i < M
    for i in range(1, min(M, N+1)):
        dp[i][i] = C[i]

    answer = INF

    for i in range(1, N+1):
        # Check if we can end here; tail gap = N-i
        for d in range(1, M+1):
            cost = dp[i][d]
            if cost >= INF:
                continue
            # ensure trailing segment has two blacks: d + (N - i) ≤ M
            if d + (N - i) <= M:
                answer = min(answer, cost)

        # Transition: from (i, d1) paint next at j = i+dist
        for d1 in range(1, M+1):
            base = dp[i][d1]
            if base >= INF:
                continue
            # dist must satisfy d1 + dist ≤ M
            maxDist = M - d1
            # j runs from i+1 to i+maxDist
            for dist in range(1, maxDist+1):
                j = i + dist
                if j > N:
                    break
                new_cost = base + C[j]
                if new_cost < dp[j][dist]:
                    dp[j][dist] = new_cost

    print(answer)

if __name__ == "__main__":
    main()
```