1 // Copyright 2011 Google Inc. All Rights Reserved. 2 3 package com.google.common.hash; 4 5 import com.google.common.collect.Sets; 6 7 import junit.framework.TestCase; 8 9 import java.util.Set; 10 11 /** 12 * Tests for HashFunctions. 13 * 14 * @author andreou@google.com (Dimitris Andreou) 15 */ 16 public class HashFunctionsTest extends TestCase { testMd5()17 public void testMd5() { 18 assertInvariants(Hashing.md5()); 19 } 20 testMurmur3_138()21 public void testMurmur3_138() { 22 assertInvariants(Hashing.murmur3_128()); 23 } 24 testMurmur3_32()25 public void testMurmur3_32() { 26 assertInvariants(Hashing.murmur3_32()); 27 } 28 testGoodFastHash()29 public void testGoodFastHash() { 30 for (int i = 1; i < 500; i++) { 31 HashFunction hasher = Hashing.goodFastHash(i); 32 assertTrue(hasher.bits() >= i); 33 assertInvariants(hasher); 34 } 35 } 36 37 /** 38 * Checks that a Hasher returns the same HashCode when given the same input, and also 39 * that the collision rate looks sane. 40 */ assertInvariants(HashFunction hashFunction)41 private static void assertInvariants(HashFunction hashFunction) { 42 int objects = 100; 43 Set<HashCode> hashcodes = Sets.newHashSetWithExpectedSize(objects); 44 for (int i = 0; i < objects; i++) { 45 Object o = new Object(); 46 HashCode hashcode1 = hashFunction.newHasher().putObject(o, HashTestUtils.BAD_FUNNEL).hash(); 47 HashCode hashcode2 = hashFunction.newHasher().putObject(o, HashTestUtils.BAD_FUNNEL).hash(); 48 assertEquals(hashcode1, hashcode2); // idempotent 49 assertEquals(hashFunction.bits(), hashcode1.bits()); 50 assertEquals(hashFunction.bits(), hashcode1.asBytes().length * 8); 51 hashcodes.add(hashcode1); 52 } 53 assertTrue(hashcodes.size() > objects * 0.95); // quite relaxed test 54 55 assertHashBytesThrowsCorrectExceptions(hashFunction); 56 } 57 assertHashBytesThrowsCorrectExceptions(HashFunction hashFunction)58 private static void assertHashBytesThrowsCorrectExceptions(HashFunction hashFunction) { 59 hashFunction.hashBytes(new byte[64], 0, 0); 60 61 try { 62 hashFunction.hashBytes(new byte[128], -1, 128); 63 fail(); 64 } catch (IndexOutOfBoundsException ok) {} 65 try { 66 hashFunction.hashBytes(new byte[128], 64, 256 /* too long len */); 67 fail(); 68 } catch (IndexOutOfBoundsException ok) {} 69 try { 70 hashFunction.hashBytes(new byte[64], 0, -1); 71 fail(); 72 } catch (IndexOutOfBoundsException ok) {} 73 } 74 } 75