hashCode()應該怎麼寫才能高效?

對於散列表,高效的hash函數是保證速度的關鍵。在java中每個對象都有自己的hashcode()函數,但hashcode()怎麼寫才高效呢?以下是jdk7系統類庫的寫法。

String類

/**
     * Seed value used for each alternative hash calculated.
     */
    private static final int HASHING_SEED;

    static {
        long nanos = System.nanoTime();
        long now = System.currentTimeMillis();
        int SEED_MATERIAL[] = {
                System.identityHashCode(String.class),
                System.identityHashCode(System.class),
                (int) (nanos >>> 32),
                (int) nanos,
                (int) (now >>> 32),
                (int) now,
                (int) (System.nanoTime() >>> 2)
        };

        // Use murmur3 to scramble the seeding material.
        // Inline implementation to avoid loading classes
        int h1 = 0;

        // body
        for (int k1 : SEED_MATERIAL) {
            k1 *= 0xcc9e2d51;
            k1 = (k1 << 15) | (k1 >>> 17);
            k1 *= 0x1b873593;

            h1 ^= k1;
            h1 = (h1 << 13) | (h1 >>> 19);
            h1 = h1 * 5 + 0xe6546b64;
        }

        // tail (always empty, as body is always 32-bit chunks)

        // finalization

        h1 ^= SEED_MATERIAL.length * 4;

        // finalization mix force all bits of a hash block to avalanche
        h1 ^= h1 >>> 16;
        h1 *= 0x85ebca6b;
        h1 ^= h1 >>> 13;
        h1 *= 0xc2b2ae35;
        h1 ^= h1 >>> 16;

        HASHING_SEED = h1;
    }

    /**
     * Cached value of the alternative hashing algorithm result
     */
    private transient int hash32 = 0;

    /**
     * Calculates a 32-bit hash value for this string.
     *
     * @return a 32-bit hash value for this string.
     */
    int hash32() {
        int h = hash32;
        if (0 == h) {
           // harmless data race on hash32 here.
           h = sun.misc.Hashing.murmur3_32(HASHING_SEED, value, 0, value.length);

           // ensure result is not zero to avoid recalcing
           h = (0 != h) ? h : 1;

           hash32 = h;
        }

        return h;
    }



Integer類

public int hashCode() {
        return value;
    }


Double類

    public int hashCode() {
        long bits = doubleToLongBits(value);
        return (int)(bits ^ (bits >>> 32));
    }

URL類

protected int hashCode(URL u) {
        int h = 0;

        // Generate the protocol part.
        String protocol = u.getProtocol();
        if (protocol != null)
            h += protocol.hashCode();

        // Generate the host part.
        InetAddress addr = getHostAddress(u);
        if (addr != null) {
            h += addr.hashCode();
        } else {
            String host = u.getHost();
            if (host != null)
                h += host.toLowerCase().hashCode();
        }

        // Generate the file part.
        String file = u.getFile();
        if (file != null)
            h += file.hashCode();

        // Generate the port part.
        if (u.getPort() == -1)
            h += getDefaultPort();
        else
            h += u.getPort();

        // Generate the ref part.
        String ref = u.getRef();
        if (ref != null)
            h += ref.hashCode();

        return h;
    }



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章