diff src/org/dancres/blitz/oid/UIDImpl.java @ 0:3dc0c5604566

Initial checkin of blitz 2.0 fcs - no installer yet.
author Dan Creswell <dan.creswell@gmail.com>
date Sat, 21 Mar 2009 11:00:06 +0000
parents
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/org/dancres/blitz/oid/UIDImpl.java	Sat Mar 21 11:00:06 2009 +0000
@@ -0,0 +1,99 @@
+package org.dancres.blitz.oid;
+
+import java.io.Serializable;
+
+import org.dancres.util.BytePacker;
+
+/**
+   A unique identifier which can be generated by an Allocator.
+ */
+final class UIDImpl implements OID {
+    static final int KEY_SIZE = 12;
+
+    private transient byte[] theKey;
+
+    private long theId;
+    private int theZoneId;
+
+    UIDImpl(byte[] aKey) {
+        theKey = aKey;
+
+        BytePacker myPacker = BytePacker.getMSBPacker(theKey);
+        theZoneId = myPacker.getInt(0);
+        theId = myPacker.getLong(4);
+    }
+
+    UIDImpl(int aZoneId, long anId) {
+        theId = anId;
+        theZoneId = aZoneId;
+    }
+
+    public int getZoneId() {
+        return theZoneId;
+    }
+
+    public long getId() {
+        return theId;
+    }
+
+    synchronized byte[] getKey() {
+        if (theKey == null) {
+            theKey = keyFor(theZoneId, theId);
+        }
+
+        return theKey;
+    }
+
+    public String toString() {
+        return " " + theZoneId + "->" + theId;
+    }
+
+    public int hashCode() {
+        /*
+          We include theZoneId to allow for the fact that all allocators for
+          a given Entry type will be allocating id's close to each other
+          because of the random allocator selection used when an id is
+          generated.  Because the id's are allocated evenly, there's a high
+          chance of two UID's allocated close together in time colliding unless
+          we also factor in theZoneId.
+         */
+        return theZoneId ^ ((int) (theId ^ (theId >>> 32)));
+    }
+
+    public int compareTo(Object anObject) {
+        UIDImpl myOther = (UIDImpl) anObject;
+
+        if (theZoneId < myOther.theZoneId)
+            return -1;
+        else if (theZoneId > myOther.theZoneId)
+            return 1;
+
+        if (theId < myOther.theId)
+            return -1;
+        else if (theId > myOther.theId)
+            return 1;
+        else
+            return 0;
+    }
+
+    public boolean equals(Object anObject) {
+        if (anObject instanceof UIDImpl) {
+            UIDImpl myOther = (UIDImpl) anObject;
+
+            return ((theZoneId == myOther.theZoneId) &&
+                    (theId == myOther.theId));
+        }
+        
+        return false;
+    }
+
+    private byte[] keyFor(int aZoneId, long anId) {
+        byte[] myKey = new byte[12];
+
+        BytePacker myPacker = BytePacker.getMSBPacker(myKey);
+        myPacker.putInt(aZoneId, 0);
+        myPacker.putLong(anId, 4);
+
+        return myKey;
+    }
+}