I'm a student, I am working on a personal project which deals with images.
basically, I'm trying to make my own image scrambler, first I convert an image into 1D array of rgb values of image.
then I send this list into this function which basically scrambles the values of list (recursively), and is also reversible:
def split_and_flip(array:list) -> list:
"""
divides the list into 2 halves and flips each half, joins the flipped halves and returns single list
does the same thing with each half recursively if the list contains even number of items,
because array with odd number items cannot be split and obtained back in original form.
where as arary with even number items can be split recursively and can be obtained back
as original form of array.
:param array: list
:return: list - modified
"""
size = len(array)
halfsize_int = size // 2
h1 = array[:halfsize_int]
h2 = array[halfsize_int:]
s1 = halfsize_int
s2 = size - halfsize_int
# first half
if s1%2==0:
h1 = split_and_flip(h1)
# second half
if s2%2==0:
h2 = split_and_flip(h2)
return h1[::-1] + h2[::-1]
but, as you can see, if the list is having odd numbers of values, the scrambling and unscrambling won't be possible. or atleast, scrambling won't be as good.
to solve this problem, I came up with this idea:
To Scramble the image:
split_and_flip(array)
on this array.To Unscrambling the image :
new_array
and do the steps 1 and 2 from above on the new array.indices
indices
, call it array
. (I am doing this step in order to obtain back the original unscrambled array of image)split_and_flip(array)
We now have successfully unscrambled the image. but while doing this, I came across this problem:
the problem I'm getting is in step 3 of unscrambling the image.
I have a list array
, and another list indices
which consists of integers. and some value val
.
I want to insert the val
in arr
at different indices, and these indices are stored in indices
.
is there a function which can do this job quickly?
I tried this code:
def insert_values(array,indices,val):
for index in indices:
array.insert(index,value)
return array
This code works, but I'm working with large arrays and there can be way too many insertions to be done depending on size of the image,
so.. my method is taking a LOT of time.
I came up with this idea of scrambling myself (idk if this is already done by someone else or not). that's why I am committed to making this work.
is there any faster way of doing this? perhaps using some library like numpy or pandas?
(I googled, but I didn't find the solution for this specific problem)
or is there any other approach for scrambling that I can take? (I really wanna do my idea though)
A simpler option would be to use random.shuffle
with a known seed
, and then 'unshuffle' the list later using the same seed.
The following program should do what you want:
import random
def shuffle(data, seed):
# Take a copy of data
shuffled = data[:]
# Set the new random seed
random.seed(seed)
# shuffle the data
random.shuffle(shuffled)
# reset the seed (to avoid problems using random elsewhere)
random.seed()
return shuffled
def unshuffle(shuffled, seed):
# Make a list of numbers the same length as the shuffled data
index = list(range(len(shuffled)))
# Shuffle this list using the same seed
index_shuffled = shuffle(index, seed)
# Zip the shuffled data and index together
unshuffled = list(zip(shuffled, index_shuffled))
# Sort the pairs to unshuffle them, and return a list of just the data values
return [x for x, y in sorted(unshuffled, key=lambda x: x[1])]
if __name__ == "__main__":
seed = 123
data = ['a', 'b', 'c', 'd', 'e']
print(data)
shuf = shuffle(data, seed)
print(shuf)
unshuf = unshuffle(shuf, seed)
print(unshuf)