Reordering numbers
I have numbers in range 1-62 I want to be able to "crypt" them, so that it's hard to guess they are generated in some order.
So, it should be some mapping, for example开发者_如何学JAVA
1->35 2->19 3->61 ...
so that I have 1 to 1 mapping, 100% reversible.
I can hardcode mapping, but I would prefer math solution to that, some kind of formula which takes number as argument, and produces number in range 1-62, and does NOT generate duplicates. Is there any chance this formula exists?
Just for history, validation script:
<?
$test = array();
$val = 37;
for($i=0;$i<62;$i++)
{
if($test[($i*$val)%62])
{
print("Collision: $i ".$test[($i*$val)%62]."<br/>");
}
$test[($i*$val)%62] = $i;
print("$i => ".(($i*$val)%62)."<br/>");
}
?>
Update:
Here are IDs generated thanks to these answers:
qpOLHk
NMb84H
aI740D
x5urn0
UsROKn
hPeb7K
EcByu7
1zYVRu
oWlieR
LjIFBe
8G52YB
v3splY
SqPMIl
fNc95I
Cazws5
ZxWTPs
mUjgcP
JhGDzc
6E30Wz
Sweeeeeet :-)
You could put the numbers 1 to 62 in an array and shuffle the array (for example using the Fisher-Yates shuffle). The index of the array is then mapped to the content of that cell (but be careful of the off-by-one error if you use 0-indexed arrays).
To make it deterministic use a particular seed for the random number generator.
Edit: A less computationally expensive (and also easier to guess) mapping is to multiply by some constant and then calculate the result modulo 62:
result = (input * 37) % 62
The number 37 is just an example. You can use any number that is coprime to 62 - that is any odd number apart from 31.
Along the lines of Mark Byers's comment. Find the inverse of x
mod n (e.g., n=62).
Let x
be your input integer in the interval [1, n]
. Use the extended Euclidean algorithm to find y
and t
such that xy + nt = 1 mod n
. Then y = x^{-1} mod n
.
Take a look at this comment on the str_rot13()
manual page.
Use RSA. It's quite easy to implement (well, depends on the language) and here's a worked example.
精彩评论