# How to shuffle a number between a range in a reversible manner

I have to generate identification number plates from a database ID. These ID are composed of three letters and three numbers e.g. BAC 212, I already have a function that convert the internal ID to the plate number:

plate_encode(0) -> 'AAA-000'
plate_encode(1) -> 'AAA-001' ... plate_decode('AAA-001') -> 1


To have a more uniform range for my plate numbers, I would like to shuffle these numbers before encoding them. This fonction act as the enigma machine, it is reversible:

seed = 32912
tumble(1, seed) -> 4839281
tumble(4839281, seed) -> 1


I could use the Enigma algorithm, but my corresponding table does not fit my plate range which is about ~2'800'000 values.

So the function I am looking for should take this additional parameter:

tumble(number, seed, max)


What kind of algorithm could I use?

• Do you need tumble to be a self-inverse? Or, would it be sufficient for there to be a separate inverse-tumble function? – poncho Jun 18 '19 at 14:44
• Separate functions are fine. – nowox Jun 18 '19 at 14:52
• The most trivial approach would be to build a static table with a 1 to 1 corresponding value for each of the 2800000 values,but I am sure there is a better solution – nowox Jun 18 '19 at 14:53
• Some of the answers to stackoverflow.com/questions/4273466/reversible-hash-function might be useful – Eugene Styer Jun 18 '19 at 15:47
• This seems a prime example where Format Preserving Encryption (FPE) could be used. Probably best used on the input ID rather than the plate numbers, as that would be more complex. – Maarten Bodewes Jun 19 '19 at 6:49