Minimising greatest distance moved
I'm trying to find if there are any solutions for a problem I've got. I've got X people and Y positions to place them in. Sometimes there might be more people than positions, but in the default case X==Y. I want to allocate the people such that the distance that any one person has to move is minimized. So if I had people开发者_运维问答 1-5 and positions A-E:
1 2 3 4 5
A B C D E
The trivial implementation I already had was assigning {A2, B3, C4, D5, E1}, which resulted in E moving much further than anyone else, when I would prefer if the matchup was {A1, B2, C3, D4, E5}, which means everyone else moves a little further, but the worst case is much smaller.
I'm currently creating an array for each person, containing each position, sorted by distance (ascending). Then I reverse sort the arrays of all the people such that the player with the highest distance to his best position is first. I allocate him to a position, then remove that position from the list of each other player, and reverse sort and repeat until all positions are filled.
This gives me reasonable results, but seems very inefficient (removing elements from each array and resorting each time)
Obviously the problem doesn't have to deal with people and distances to positions, but can be said to be allocating resources, where each resource can perform a task with a certain fitness, and I want to avoid using a tool that is grossly unsuitable for a given task, even if it means every tool is doing a task that is slightly unsuitable, if that makes sense.
I suspect that there is some classic optimization problem that I'm mirroring here, but I don't know which one.
Move everyone to the middle. That is, for each person; if they are the i
'th leftmost person then they go in the i
'th slot.
Proof of optimality:
Jumping over someone isn't advantageous because you could just shift those people a lesser amount and yourself a lesser amount and the amount of moves used is the same.
ex: A _ B _ _ C _ _ 1 2 3
A must move at least 7 slots to get to the boundary, then position himself on a square.
B must move at least 5 ...
C must move at least 2 ...
Then we see we have 1,2,3 moves left to allocate, so jumping over each other still always resolves in 7+5+2+1+2+3 moves. And in the case where there are characters to the right, if any of those jump over leftmost characters then that means a left character has to make additional moves to be on the right side of the slots.
Therefore jumping leads to a equal or greater number of moves, it is never advantageous.
Now since jumping gains nothing the only operations are to move or stop. If character i
moves to a slot after i
, then someone to the right of him will have to jump over leftwards or they can't all be aligned. Likewise if character i
ends up before slot i
, someone to the left will have to jump over him towards the right.
That wasn't so bad
精彩评论