Merge "delete hello example"
[aaa.git] / aaa-authn / src / main / java / org / opendaylight / aaa / HashCodeUtil.java
1 /*****************************************************************************
2  * Copyright (c) 2014 Hewlett-Packard Development Company, L.P. and others.
3  *
4  * All rights reserved. This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License v1.0
6  * which accompanies this distribution, and is available at
7  * http://www.eclipse.org/legal/epl-v10.html
8  *****************************************************************************/
9 package org.opendaylight.aaa;
10
11 import java.lang.reflect.Array;
12
13 /**
14  * Collected methods which allow easy implementation of <tt>hashCode</tt>.
15  *
16  * Example use case:
17  *
18  * <pre>
19  * public int hashCode() {
20  *     int result = HashCodeUtil.SEED;
21  *     // collect the contributions of various fields
22  *     result = HashCodeUtil.hash(result, fPrimitive);
23  *     result = HashCodeUtil.hash(result, fObject);
24  *     result = HashCodeUtil.hash(result, fArray);
25  *     return result;
26  * }
27  * </pre>
28  */
29 public final class HashCodeUtil {
30
31     /**
32      * An initial value for a <tt>hashCode</tt>, to which is added contributions
33      * from fields. Using a non-zero value decreases collisions of
34      * <tt>hashCode</tt> values.
35      */
36     public static final int SEED = 23;
37
38     /** booleans. */
39     public static int hash(int aSeed, boolean aBoolean) {
40         return firstTerm(aSeed) + (aBoolean ? 1 : 0);
41     }
42
43     /*** chars. */
44     public static int hash(int aSeed, char aChar) {
45         return firstTerm(aSeed) + aChar;
46     }
47
48     /** ints. */
49     public static int hash(int aSeed, int aInt) {
50         return firstTerm(aSeed) + aInt;
51     }
52
53     /** longs. */
54     public static int hash(int aSeed, long aLong) {
55         return firstTerm(aSeed) + (int) (aLong ^ (aLong >>> 32));
56     }
57
58     /** floats. */
59     public static int hash(int aSeed, float aFloat) {
60         return hash(aSeed, Float.floatToIntBits(aFloat));
61     }
62
63     /** doubles. */
64     public static int hash(int aSeed, double aDouble) {
65         return hash(aSeed, Double.doubleToLongBits(aDouble));
66     }
67
68     /**
69      * <tt>aObject</tt> is a possibly-null object field, and possibly an array.
70      *
71      * If <tt>aObject</tt> is an array, then each element may be a primitive or
72      * a possibly-null object.
73      */
74     public static int hash(int aSeed, Object aObject) {
75         int result = aSeed;
76         if (aObject == null) {
77             result = hash(result, 0);
78         } else if (!isArray(aObject)) {
79             result = hash(result, aObject.hashCode());
80         } else {
81             int length = Array.getLength(aObject);
82             for (int idx = 0; idx < length; ++idx) {
83                 Object item = Array.get(aObject, idx);
84                 // if an item in the array references the array itself, prevent
85                 // infinite looping
86                 if (!(item == aObject)) {
87                     result = hash(result, item);
88                 }
89             }
90         }
91         return result;
92     }
93
94     // PRIVATE
95     private static final int fODD_PRIME_NUMBER = 37;
96
97     private static int firstTerm(int aSeed) {
98         return fODD_PRIME_NUMBER * aSeed;
99     }
100
101     private static boolean isArray(Object aObject) {
102         return aObject.getClass().isArray();
103     }
104 }