Уменьшение время исполнения кода

Всем привет! Сразу прошу не бить тапками за такой код, главное, что он корректно работает. Дайте совет, пожалуйста, что можно сделать для того, чтобы сократить время исполнения кода? Вкратце что делает код :

s - количество списков на проверку, k - число цифр, которые нужно удалить в списках, n - кол-во чисел в списке, mobs_list - сам список

Код по задумке должен удалить k чисел так, чтобы при делении mobs_list на две части (p1/p2) левая сторона была максимально больше, чем правая...

пробовал добавлять штуки по типу : (но это не сильно помогло)

    for _ in range(len(mobs_list)//2):
        n = len(mobs_list)
        if k%2 != 0 and (k>=2):
            k-=2
            if max(mobs_list[n//2::])<min(mobs_list[:n//2:]):
                mobs_list.remove(min(mobs_list[:n//2:]))

p.s. Сначала вроде "красивый", "по всем правилам" код я писал через создание функций, но таким образом я слишком много использовал памяти :(

s = int(input())
answer = []
for _ in range(s):
    n, k = map(int, input().split())
    mobs_list = list(map(int, input().split()))
    
    if k == 0:
        answer.append(sum(mobs_list[:n//2:]) - sum(mobs_list[n//2::]))
    else:
        while k != 0:
            n = len(mobs_list)
            if k % 2 == 0: #скрипт для чётных
                keys = [str(key) for key in range(1,6)]
                
                var = dict.fromkeys(keys)
                
                ans = []
                
                # 1 удаляем последние 2 в part_1
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p1.pop(-1)
                p1.pop(-1)
                p1.append(p2[0])
                p2.pop(0)
                var["1"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))
                
                # 2 удаляем последний в part_1
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p1.pop(-1)
                p2.remove(max(p2))
                var["2"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))
                
                # 3 удаляем 2 в part_1
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p1.remove(min(p1))
                p1.append(p2[0])
                p1.remove(min(p1))
                p2.pop(0)
                var["3"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))          
                
                # 4 удаляем 2 в part_2
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p2.remove(max(p2))
                p2.remove(max(p2))
                p2.append(p1[-1])
                p1.pop(-1)
                var["4"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))
                
                # 5 удаляем 1 в part_1 и 1 в part_2
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p1.remove(min(p1))
                p2.remove(max(p2))
                var["5"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))

                
                ind = str(ans.index(max(ans))+1)
                mobs_list = var[ind][0]+var[ind][1]

                k -= 2
                n -= 2
                
                if k == 0: answer.append(sum(mobs_list[:n//2:]) - sum(mobs_list[n//2::]))
                
            else: #скрипт для нечётных
                keys = [str(key) for key in range(1,5)]
                
                var = dict.fromkeys(keys)
                
                ans = []

                # 1 удаляем последний в part_1
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p1.pop(-1)
                p1.append(p2[0])
                p2.pop(0)
                var["1"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))

                # 2 удаляем первый в part_2
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p2.pop(0)
                var["2"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))

                # 3 удаляем в part_1
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p1.remove(min(p1))
                p1.append(p2[0])
                p2.pop(0)
                var["3"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))
                
                # 4 удаляем в part_2
                p1, p2 = mobs_list[:n//2:], mobs_list[n//2::]
                p2.remove(max(p2))
                var["4"] = [p1,p2]
                ans.append(sum(p1)-sum(p2))

                
                ind = str(ans.index(max(ans))+1)
                mobs_list = var[ind][0]+var[ind][1]

                k -= 1
                n -= 1
                
                if k == 0: answer.append(sum(mobs_list[:n//2:]) - sum(mobs_list[n//2::]))

for item in answer: print(item)

Ответы (1 шт):

Автор решения: MBo

Прогоним точку разделения списков, начиная с позиции i=m=(n-k)//2.

В левой части на первом шаге удалять нечего, в правой части нужно убрать (из подсчёта, не физически) k наибольших элементов, оставив m наименьших. Считаем разность сумм.

На следующем шаге сдвигаем i вправо, теперь из левой части нужно удалить один наименьший элемент, оставив m наибольших. Из правой части один элемент ушёл влево, поэтому для неё m наименьших могут измениться (может участвовать элемент, который на прошлом шаге не участвовал в сумме). Считаем разность сумм, сравниваем с имеющейся.

Продолжаем до позиции i=n-m

Остаётся подобрать структуру данных, быструю и удобную для поддержания m наибольших и m наименьших

Ориентир - время O(nlogn), т.е. на указанные обновления должно тратиться логарифмическое время

→ Ссылка