Reputation: 191
So I've been doing some sorting algorithms and I want to run a test function that generates lists of different varieties to run my sorting algorithms on.
One such list would be an already sorted list, where n number of the items in the list have been shuffled around randomly (but not all of them, the list should still be sorted other than the n items)
testlist = random.sample(range(0,10),10)
testlist.sort()
This gives me a sorted list of unique items of size 10, but then I'm unsure how to go about moving n of these 10 items around the list to a random location, just to mix the sorting up
Upvotes: 9
Views: 2137
Reputation: 37509
Something like this would work. Basically, just pick two indexes at random and switch them, and not switching the same index more than once. If run on a sorted array, it does guarantee that exactly n
elements are unsorted. Only works on even number replacements though.
array = list(range(10))
def shuffle_n(array, n):
assert n <= len(array) and n % 2 == 0
indexes = set(range(len(array)))
for i in range(n // 2):
a, b = random.sample(indexes, 2)
indexes.remove(a)
indexes.remove(b)
array[a], array[b] = array[b], array[a]
Upvotes: 2
Reputation: 77837
Here's a controlled implementation. Pick four indices at random to get switched. Shuffle those values, and put them back into the four designated spots. Note that it does not guarantee that the new values will all be different.
import random
import copy
testlist = random.sample(range(0, 20), 10)
testlist.sort()
print testlist
n = 4
move_set = set()
while len(move_set) < n:
move_set.add(random.randrange(0, 10))
print move_set
move_list = list(move_set)
# Replace n elements
test1 = copy.copy(testlist)
migrant = [test1[_] for _ in move_set]
random.shuffle(migrant)
print migrant
test_case = []
for i in range(n):
test1[move_list[i]] = migrant[i]
print test1
Output:
[0, 3, 4, 5, 7, 8, 9, 12, 16, 17]
set([9, 3, 4, 5])
[5, 17, 8, 7]
[0, 3, 4, 17, 8, 7, 9, 12, 16, 5]
In this run, it's only coincidence that all four indices were also values in the list. Elements 9, 3, 4, and 5 have values 17, 5, 7, and 8, respectively. The shuffle puts each of the four into new locations.
Upvotes: 3
Reputation: 8122
Here's one way to shuffle some items in the list:
import random
import numpy as np
# Make a sorted list of integers.
x = np.array(range(100))
# Choose 10 indices at random.
r = random.sample(range(len(x)), 10)
# Copy this list and shuffle.
s = r.copy()
random.shuffle(s)
# Replace the indices with the shuffled ones.
x[r] = x[s]
Note this might leave some indices unchanged.
Upvotes: 5