I need to swap the max and min in a list of distinct numbers. Like so:
Example input
3 4 5 2 1
Example output
3 4 1 2 5
I figured using this would make the most sense:
a = [3, 4, 5, 2, 1]
a[a.index(max(a))], a[a.index(min(a))] = min(a), max(a)
However, it seems to work on some lists of distinct numbers but not others (including the given example). I have no idea why. Can anyone see the bug?
In multiple assignments, Python calculates all of the right hand side parts, left to right, then assigns them one by one to the left hand side parts, left to right (see the language reference for details). So:
a = [3, 4, 5, 2, 1]
a[a.index(max(a))], a[a.index(min(a))] = min(a), max(a)
a = [3, 4, 5, 2, 1]
a[a.index(max(a))], a[a.index(min(a))] = 1, max(a)
a = [3, 4, 5, 2, 1]
a[a.index(max(a))], a[a.index(min(a))] = 1, 5
a = [3, 4, 5, 2, 1]
a[a.index(5)], a[a.index(min(a))] = 1, 5
a = [3, 4, 5, 2, 1]
a[2], a[a.index(min(a))] = 1, 5
a = [3, 4, 1, 2, 1]
a[a.index(min(a))] = 5
a = [3, 4, 1, 2, 1]
a[a.index(1)] = 5
a = [3, 4, 1, 2, 1]
a[2] = 5
# ^ uh oh
a = [3, 4, 5, 2, 1]
If the minimum value is before the maximum value this works fine, because we always replace the first occurrence of the minimum value and that turns out to be the original one.
To fix it, just calculate the indices separately before doing the swap.