When I am encrypting 23
using MD5 encryption I am getting 37693cfc748049e45d87b8c7d8b9aacd
this 32-character long string which will always be static for 23.
I want the same kind of mechanism but that should generate 18 or less (like: 122ff1e4883358b6
) characters long string instead 32.
How I can do that in C#, is there any shorter version of MD5 in c#??
I like @RichieHindle's answer. However, if you're interested in losing fewer bits of fidelity (and thereby decreasing the risk of collisions), you could take the 128 bit value returned by the MD5 Hash, and encode it using ASCII85 (also known as Base85 encoding), instead of a hexadecimal-based encoding. This will give you the whole hash in 20 bytes (which is more than you wanted, but you could chop 2 bytes off, resulting in much less loss than removing 14 of the 32 bytes you'd get using hex encoding).
Edit: Prashant says 20 characters is close enough, and asked for sample code:
After obtaining the MD5 hash from the MD5.ComputeHash call, you can use Jeff Atwood's ASCII85 encoder:
MD5 m = MD5.Create();
byte[] hash = m.ComputeHash(System.Text.Encoding.ASCII.GetBytes("23"));
Ascii85 encoder = new Ascii85();
encoder.EnforceMarks = false;
string hash85 = encoder.Encode(hash);
Console.Out.WriteLine(hash85);
Yields
2ebDPFFZsD?&,r1fX\$,
so you can just use hash85
. The encoder.EnforceMarks
makes sure that the encoding doesn't include some typical prefix and suffixes that are associated with ASCII85.
You can just take as much of the MD5 hash as you need, and throw the rest away. All the bits have equal value, so there's no difference between doing that and using some hashing algorithm that natively produces fewer bits.
(If you're doing this for security reasons, remember that fewer bits makes hashes easier to crack, regardless of the algorithm. Even outside of security applications, fewer bits increase the risk of collisions. Also bear in mind that MD5 is relative insecure these days - SHA-1 or SHA-2 are considered more secure.)
MD5 always creates a 128 Bit Hash.
Other smaller Hashtypes (taken from Wikipedia)
Fowler-Noll-Vo hash function (32, 64, 128, 256, 512, or 1024 bits)
Jenkins hash function (32 bits)
MurmurHash (32 or 64 bits)
Pearson hashing (8 bits)
But remember hash collisions
Use FVNHash - http://www.codeproject.com/KB/security/FnvHash.aspx
You can set the length of your hash, do not use it for security reasons.
I wouldn't use a hash function if you want to be able to map the result back to its original value without collisions.
If your aim is to turn a small decimal number into a long obfuscated string, just invent some mapping algorithm and encode the result with zBase32 or similar.
public string Obfuscate(long x)
{
return ToZBase32(BitConverter.GetBytes(x * 63498398L));
}
public long Deobfuscate(string x)
{
return BitConverter.ToInt64(FromZBase32(x)) / 63498398L;
}
23
gets encoded to "gmuyaiayyyyyy"
. (63498398 chosen by fair dice roll.)
shortest useful hash algorithm would be md5 . generates 16 bytes=128 bit hash. if you use base 64 encoding ...that is 6 useful bits per byte/char.
u should be able to reduce the md5 to 22 characters (ascii). what you have is hex version where 2 bytes represent one actual byte
(leaving the trailing padding introduced by b64)
with an added advantage of using the same for legal filenames. (ofcourse u will have to substitute the default / and + characters with any other symbol which does not clash with file naming convention of your os.
base64 (by replacing / and +) ensures your hash doesnot mess up the url with special characters which may mean something else to your webserver
ASCII85 adds characters which are difficult to deal with when using as filenames and in urls
'37aa3296c523f6c5a7fd2102a9155dcc' (hex) (32 bytes)
[55, 170, 50, 150, 197, 35, 246, 197, 167, 253, 33, 2, 169, 21, 93, 204] = (16 Bytes)
N6oylsUj9sWn_SECqRVdzA==
My Final Hash
N6oylsUj9sWn_SECqRVdzA this is actually the complete md5 in 22 ascii characters
([you can strip the two trailing = there will always be two for md5-add them later when decoding. also replace + and / characters in b64 with any other i prefer -(dash) and _ (underscore) ]
this 32-character long string are number from hexadecimal : 0-f you can make it shorter by converting its hexadecimal value to radix of 36 : 0-z
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With