better initial hash computation

git-svn-id: https://svn.berlios.de/svnroot/repos/yacy/trunk@7157 6c8d7289-2bf4-0310-a012-ef5d649a1542
pull/1/head
orbiter 15 years ago
parent 34e2f7f487
commit 89c2d8b81e

@ -659,29 +659,44 @@ public class yacySeed implements Cloneable {
}
private static byte[] bestGap(final yacySeedDB seedDB) {
byte[] randomHash = randomHash();
if ((seedDB == null) || (seedDB.sizeConnected() <= 2)) {
// use random hash
return randomHash();
return randomHash;
}
// find gaps
final TreeMap<Long, String> gaps = hashGaps(seedDB);
// take one gap; prefer biggest but take also another smaller by chance
String interval = null;
final Random r = new Random();
while (!gaps.isEmpty()) {
interval = gaps.remove(gaps.lastKey());
if (r.nextBoolean()) break;
if (random.nextBoolean()) break;
}
if (interval == null) return randomHash();
// find dht position and size of gap
final long gaphalf = FlatWordPartitionScheme.dhtDistance(
FlatWordPartitionScheme.std.dhtPosition(interval.substring(0, 12).getBytes(), null),
FlatWordPartitionScheme.std.dhtPosition(interval.substring(12).getBytes(), null)) >> 1;
long p = FlatWordPartitionScheme.std.dhtPosition(interval.substring(0, 12).getBytes(), null);
long gappos = (Long.MAX_VALUE - p >= gaphalf) ? p + gaphalf : (p - Long.MAX_VALUE) + gaphalf;
return FlatWordPartitionScheme.positionToHash(gappos);
long left = FlatWordPartitionScheme.std.dhtPosition(interval.substring(0, 12).getBytes(), null);
long right = FlatWordPartitionScheme.std.dhtPosition(interval.substring(12).getBytes(), null);
final long gap4 = FlatWordPartitionScheme.dhtDistance(left, right) >> 2; // a quarter of a gap
long gapx = gap4;
if (random.nextBoolean()) gapx += gap4;
if (random.nextBoolean()) gapx += gap4;
long gappos = (Long.MAX_VALUE - left >= gapx) ? left + gapx : (left - Long.MAX_VALUE) + gapx;
byte[] computedHash = FlatWordPartitionScheme.positionToHash(gappos);
// the computed hash is the perfect position (modulo gap4 population and gap alternatives)
// this is too tight. The hash must be more randomized. We take only (!) the first two bytes
// of the computed hash and add random bytes at the remaining positions. The first two bytes
// of the hash may have 64*64 = 2^^10 positions, good for over 1 million peers.
byte[] combined = new byte[12];
System.arraycopy(computedHash, 0, combined, 0, 2);
System.arraycopy(randomHash, 2, combined, 2, 10);
// finally check if the hash is already known
while (seedDB.hasConnected(combined) || seedDB.hasDisconnected(combined) || seedDB.hasPotential(combined)) {
// if we are lucky then this loop will never run
combined = randomHash();
}
return combined;
}
private static TreeMap<Long, String> hashGaps(final yacySeedDB seedDB) {

Loading…
Cancel
Save