Main Page | Class Hierarchy | Data Structures | Directories | File List | Data Fields | Related Pages

KeyRange.java

00001 /*-
00002  * See the file LICENSE for redistribution information.
00003  *
00004  * Copyright (c) 2002-2005
00005  *      Sleepycat Software.  All rights reserved.
00006  *
00007  * $Id: KeyRange.java,v 12.1 2005/01/31 19:27:32 mark Exp $
00008  */
00009 
00010 package com.sleepycat.collections;
00011 
00012 import java.util.Comparator;
00013 
00014 import com.sleepycat.db.DatabaseEntry;
00015 
00019 class KeyRange {
00020 
00021     Comparator comparator;
00022     DatabaseEntry beginKey;
00023     DatabaseEntry endKey;
00024     boolean singleKey;
00025     boolean beginInclusive;
00026     boolean endInclusive;
00027 
00031     KeyRange(Comparator comparator) {
00032         this.comparator = comparator;
00033     }
00034 
00038     KeyRange subRange(DatabaseEntry key)
00039         throws KeyRangeException {
00040 
00041         if (!check(key)) {
00042             throw new KeyRangeException("singleKey out of range");
00043         }
00044         KeyRange range = new KeyRange(comparator);
00045         range.beginKey = key;
00046         range.endKey = key;
00047         range.beginInclusive = true;
00048         range.endInclusive = true;
00049         range.singleKey = true;
00050         return range;
00051     }
00052 
00057     KeyRange subRange(DatabaseEntry beginKey, boolean beginInclusive,
00058                       DatabaseEntry endKey, boolean endInclusive)
00059         throws KeyRangeException {
00060 
00061         if (beginKey == null) {
00062             beginKey = this.beginKey;
00063             beginInclusive = this.beginInclusive;
00064         } else if (!check(beginKey, beginInclusive)) {
00065             throw new KeyRangeException("beginKey out of range");
00066         }
00067         if (endKey == null) {
00068             endKey = this.endKey;
00069             endInclusive = this.endInclusive;
00070         } else if (!check(endKey, endInclusive)) {
00071             throw new KeyRangeException("endKey out of range");
00072         }
00073         KeyRange range = new KeyRange(comparator);
00074         range.beginKey = beginKey;
00075         range.endKey = endKey;
00076         range.beginInclusive = beginInclusive;
00077         range.endInclusive = endInclusive;
00078         return range;
00079     }
00080 
00085     final DatabaseEntry getSingleKey() {
00086 
00087         return singleKey ? beginKey : null;
00088     }
00089 
00093     final boolean hasBound() {
00094 
00095         return endKey != null || beginKey != null;
00096     }
00097 
00101     public String toString() {
00102 
00103         return "[KeyRange " + beginKey + ' ' + beginInclusive +
00104                               endKey + ' ' + endInclusive +
00105                               (singleKey ? " single" : "");
00106     }
00107 
00111     boolean check(DatabaseEntry key) {
00112 
00113         if (singleKey) {
00114             return (compare(key, beginKey) == 0);
00115         } else {
00116             return checkBegin(key, true) && checkEnd(key, true);
00117         }
00118     }
00119 
00123     boolean check(DatabaseEntry key, boolean inclusive) {
00124 
00125         if (singleKey) {
00126             return (compare(key, beginKey) == 0);
00127         } else {
00128             return checkBegin(key, inclusive) && checkEnd(key, inclusive);
00129         }
00130     }
00131 
00148     boolean checkBegin(DatabaseEntry key, boolean inclusive) {
00149 
00150         if (beginKey == null) {
00151             return true;
00152         } else if (!beginInclusive && inclusive) {
00153             return compare(key, beginKey) > 0;
00154         } else {
00155             return compare(key, beginKey) >= 0;
00156         }
00157     }
00158 
00163     boolean checkEnd(DatabaseEntry key, boolean inclusive) {
00164 
00165         if (endKey == null) {
00166             return true;
00167         } else if (!endInclusive && inclusive) {
00168             return compare(key, endKey) < 0;
00169         } else {
00170             return compare(key, endKey) <= 0;
00171         }
00172     }
00173 
00177     int compare(DatabaseEntry key1, DatabaseEntry key2) {
00178 
00179         if (comparator != null) {
00180             return comparator.compare(getByteArray(key1), getByteArray(key2));
00181         } else {
00182             return compareBytes
00183                     (key1.getData(), key1.getOffset(), key1.getSize(),
00184                      key2.getData(), key2.getOffset(), key2.getSize());
00185 
00186         }
00187     }
00188 
00193     static int compareBytes(byte[] data1, int offset1, int size1,
00194                             byte[] data2, int offset2, int size2) {
00195 
00196         for (int i = 0; i < size1 && i < size2; i++) {
00197 
00198             int b1 = 0xFF & data1[offset1 + i];
00199             int b2 = 0xFF & data2[offset2 + i];
00200             if (b1 < b2)
00201                 return -1;
00202             else if (b1 > b2)
00203                 return 1;
00204         }
00205 
00206         if (size1 < size2)
00207             return -1;
00208         else if (size1 > size2)
00209             return 1;
00210         else
00211             return 0;
00212     }
00213 
00217     static DatabaseEntry copy(DatabaseEntry from) {
00218         return new DatabaseEntry(getByteArray(from));
00219     }
00220 
00224     static void copy(DatabaseEntry from, DatabaseEntry to) {
00225         to.setData(getByteArray(from));
00226         to.setOffset(0);
00227     }
00228 
00233     static byte[] getByteArray(DatabaseEntry entry) {
00234 
00235         byte[] bytes = entry.getData();
00236         if (bytes == null) return null;
00237         int size = entry.getSize();
00238         byte[] data = new byte[size];
00239         System.arraycopy(bytes, entry.getOffset(), data, 0, size);
00240         return data;
00241     }
00242 
00246     static boolean equalBytes(DatabaseEntry e1, DatabaseEntry e2) {
00247 
00248         if (e1 == null && e2 == null) {
00249             return true;
00250         }
00251         if (e1 == null || e2 == null) {
00252             return false;
00253         }
00254 
00255         byte[] d1 = e1.getData();
00256         byte[] d2 = e2.getData();
00257         int s1 = e1.getSize();
00258         int s2 = e2.getSize();
00259         int o1 = e1.getOffset();
00260         int o2 = e2.getOffset();
00261 
00262         if (d1 == null && d2 == null) {
00263             return true;
00264         }
00265         if (d1 == null || d2 == null) {
00266             return false;
00267         }
00268         if (s1 != s2) {
00269             return false;
00270         }
00271         for (int i = 0; i < s1; i += 1) {
00272             if (d1[o1 + i] != d2[o2 + i]) {
00273                 return false;
00274             }
00275         }
00276         return true;
00277     }
00278 
00287     static String toString(DatabaseEntry dbt) {
00288 
00289         int len = dbt.getOffset() + dbt.getSize();
00290         StringBuffer buf = new StringBuffer(len * 2);
00291         byte[] data = dbt.getData();
00292         for (int i = dbt.getOffset(); i < len; i++) {
00293             String num = Integer.toHexString(data[i]);
00294             if (num.length() < 2) buf.append('0');
00295             buf.append(num);
00296         }
00297         return buf.toString();
00298     }
00299 }

Generated on Sun Dec 25 12:14:31 2005 for Berkeley DB 4.4.16 by  doxygen 1.4.2