Skip to content

Instantly share code, notes, and snippets.

@soon
Created April 21, 2015 18:12
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save soon/2192e387ee4041be1844 to your computer and use it in GitHub Desktop.
Save soon/2192e387ee4041be1844 to your computer and use it in GitHub Desktop.
from functools import reduce
from itertools import count, permutations
from pprint import pprint
def to_task_name(n):
return chr(ord('A') + n)
def name_time_cost_to_task(t):
return {
'name': t[0],
'time': t[1],
'cost': t[2]
}
def solve_for_ordered_tasks(ordered_tasks):
total_time = sum(map(lambda t: t['time'], ordered_tasks))
def reduce_function(acc, t):
return {
'time_left': acc['time_left'] - t['time'],
'total_cost': acc['total_cost'] + (acc['time_left'] - t['time']) * t['cost']
}
total_cost = reduce(reduce_function, ordered_tasks, {'time_left': total_time, 'total_cost': 0})['total_cost']
return {
'ordered_tasks': ordered_tasks,
'total_cost': total_cost
}
def create_tasks_iter(costs, time):
return map(name_time_cost_to_task, zip(map(to_task_name, count()), time, costs))
def solve(costs, time):
tasks = create_tasks_iter(costs, time)
ordered_tasks = sorted(tasks, key=lambda t: t['cost'] / t['time'])
return solve_for_ordered_tasks(ordered_tasks)
def order_tasks(tasks, order):
return [next(t for t in tasks if t['name'] == o) for o in order]
def run_test_1():
costs = [22, 1, 10, 4, 9]
time = [11, 1, 6, 3, 4]
ans = solve(costs, time)
assert ans['total_cost'] == 346, '{} is not equal to {}'.format(ans['total_cost'], 346)
print("Test 1 passed")
def run_test_2():
costs = [7, 2, 18, 1, 14, 5]
time = [4, 3, 9, 1, 6, 3]
ans = solve(costs, time)
assert ans['total_cost'] == 376, '{} is not equal to {}'.format(ans['total_cost'], 376)
print("Test 2 passed")
def get_worst_case(costs, time):
tasks = list(create_tasks_iter(costs, time))
order = [t['name'] for t in tasks]
worst = max((solve_for_ordered_tasks(order_tasks(tasks, o)) for o in permutations(order)),
key=lambda ans: ans['total_cost'])
return worst
def main():
run_test_1()
run_test_2()
costs = list(map(int, input('Enter costs: ').split()))
time = list(map(int, input('Enter times: ').split()))
pprint(solve(costs, time))
worst_case = get_worst_case(costs, time)
pprint(worst_case)
# while True:
# tasks = list(create_tasks_iter(costs, time))
# order = [x.upper() for x in input('Enter order: ').split()]
# ordered_tasks = order_tasks(tasks, order)
# pprint(solve_for_ordered_tasks(ordered_tasks))
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment