← Home
package main

import (
	"bufio"
	"fmt"
	"os"
	"sort"
	"strconv"
)

type BIT struct {
	cnt  []int
	sum  []int64
	vals []int64
	M    int
}

func NewBIT(vals []int64) *BIT {
	M := len(vals)
	return &BIT{
		cnt:  make([]int, M+1),
		sum:  make([]int64, M+1),
		vals: vals,
		M:    M,
	}
}

func (b *BIT) Add(idx int, cntDelta int, sumDelta int64) {
	for i := idx; i <= b.M; i += i & -i {
		b.cnt[i] += cntDelta
		b.sum[i] += sumDelta
	}
}

func (b *BIT) Query(k int) int64 {
	if k <= 0 {
		return 0
	}
	if b.M == 0 {
		return 0
	}
	k_rem := k
	sum := int64(0)
	idx := 0
	for i := 17; i >= 0; i-- {
		nextIdx := idx + (1 << i)
		if nextIdx <= b.M && b.cnt[nextIdx] <= k_rem {
			k_rem -= b.cnt[nextIdx]
			sum += b.sum[nextIdx]
			idx = nextIdx
		}
	}
	if k_rem > 0 && idx < b.M {
		sum += int64(k_rem) * b.vals[idx]
	}
	return sum
}

func solveMax(a []int64, length int, k int) int64 {
	n := len(a)
	var negs []int64
	for _, x := range a {
		if x < 0 {
			negs = append(negs, x)
		}
	}
	sort.Slice(negs, func(i, j int) bool { return negs[i] < negs[j] })
	var vals []int64
	if len(negs) > 0 {
		vals = append(vals, negs[0])
		for i := 1; i < len(negs); i++ {
			if negs[i] != negs[i-1] {
				vals = append(vals, negs[i])
			}
		}
	}

	b := NewBIT(vals)

	getIdx := func(v int64) int {
		idx := sort.Search(len(vals), func(i int) bool { return vals[i] >= v })
		if idx < len(vals) && vals[idx] == v {
			return idx + 1
		}
		return -1
	}

	var currentSum int64 = 0
	for i := 0; i < length; i++ {
		currentSum += a[i]
		if a[i] < 0 {
			b.Add(getIdx(a[i]), 1, a[i])
		}
	}

	maxSum := currentSum - 2*b.Query(k)

	for i := length; i < n; i++ {
		currentSum += a[i]
		if a[i] < 0 {
			b.Add(getIdx(a[i]), 1, a[i])
		}
		currentSum -= a[i-length]
		if a[i-length] < 0 {
			b.Add(getIdx(a[i-length]), -1, -a[i-length])
		}

		cand := currentSum - 2*b.Query(k)
		if cand > maxSum {
			maxSum = cand
		}
	}

	return maxSum
}

func main() {
	scanner := bufio.NewScanner(os.Stdin)
	scanner.Split(bufio.ScanWords)

	if !scanner.Scan() {
		return
	}
	n, _ := strconv.Atoi(scanner.Text())
	scanner.Scan()
	length, _ := strconv.Atoi(scanner.Text())

	a := make([]int64, n)
	for i := 0; i < n; i++ {
		scanner.Scan()
		a[i], _ = strconv.ParseInt(scanner.Text(), 10, 64)
	}

	scanner.Scan()
	k, _ := strconv.Atoi(scanner.Text())

	ans1 := solveMax(a, length, k)

	nega := make([]int64, n)
	for i := 0; i < n; i++ {
		nega[i] = -a[i]
	}
	ans2 := solveMax(nega, length, k)

	if ans1 > ans2 {
		fmt.Println(ans1)
	} else {
		fmt.Println(ans2)
	}
}