Skip to content

Commit 1018f3e

Browse files
committed
Minor optimisation to Index encoding (save a byte in leaf entries)
1 parent e30c49b commit 1018f3e

File tree

3 files changed

+34
-31
lines changed

3 files changed

+34
-31
lines changed

convex-core/src/main/java/convex/core/data/Index.java

Lines changed: 32 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ public final class Index<K extends ABlobLike<?>, V extends ACell> extends AIndex
4747

4848
/**
4949
* Entry for this node of the radix tree. Invariant assumption that the prefix
50-
* is correct. May be null if there is no entry at this node.
50+
* is correct. Will be null if there is no entry at this node.
5151
*/
5252
private final MapEntry<K, V> entry;
5353

@@ -518,14 +518,28 @@ public int encodeRaw(byte[] bs, int pos) {
518518
pos = Format.writeVLCCount(bs,pos, count);
519519
if (count == 0) return pos; // nothing more to know... this must be the empty singleton
520520

521-
pos = MapEntry.encodeCompressed(entry,bs,pos); // entry may be null
522-
if (count == 1) return pos; // must be a single entry
521+
if (count == 1) {
522+
// directly encode single entry
523+
pos=entry.getKeyRef().encode(bs,pos);
524+
pos=entry.getValueRef().encode(bs,pos);
525+
return pos; // must be a single entry, exit early
526+
} else {
527+
if (entry==null) {
528+
bs[pos++]=Tag.NULL; // no entry present
529+
} else {
530+
bs[pos++]=Tag.VECTOR;
531+
pos=entry.getKeyRef().encode(bs,pos);
532+
pos=entry.getValueRef().encode(bs,pos);
533+
}
534+
}
523535

524536
// We only have a meaningful depth if more than one entry
525537
bs[pos++] = (byte)depth;
538+
539+
// write mask
540+
pos = Utils.writeShort(bs,pos,mask);
526541

527542
// finally write children
528-
pos = Utils.writeShort(bs,pos,mask);
529543
int n = children.length;
530544
for (int i = 0; i < n; i++) {
531545
pos = encodeChild(bs,pos,i);
@@ -559,14 +573,22 @@ public static <K extends ABlobLike<?>, V extends ACell> Index<K, V> read(Blob b,
559573
if (count < 0) throw new BadFormatException("Negative count!");
560574
if (count == 0) return (Index<K, V>) EMPTY;
561575

576+
// index for reading
562577
int epos=pos+1+Format.getVLCCountLength(count);
563578

564-
565-
byte etype=b.byteAt(epos++);
566579
MapEntry<K,V> me;
567-
if (etype==Tag.NULL) {
568-
me=null;
569-
} else if (etype==Tag.VECTOR){
580+
boolean hasEntry;
581+
if (count==1) {
582+
hasEntry=true;
583+
} else {
584+
byte c=b.byteAt(epos++); // Read byte
585+
switch (c) {
586+
case Tag.NULL: hasEntry=false; break;
587+
case Tag.VECTOR: hasEntry=true; break;
588+
default: throw new BadFormatException("Invalid MapEntry tag in Index: "+c);
589+
}
590+
}
591+
if (hasEntry) {
570592
Ref<K> kr=Format.readRef(b,epos);
571593
epos+=kr.getEncodingLength();
572594
Ref<V> vr=Format.readRef(b,epos);
@@ -581,7 +603,7 @@ public static <K extends ABlobLike<?>, V extends ACell> Index<K, V> read(Blob b,
581603
return result;
582604
}
583605
} else {
584-
throw new BadFormatException("Invalid MapEntry tag in Index: "+etype);
606+
me=null;
585607
}
586608

587609
Index<K,V> result;

convex-core/src/main/java/convex/core/data/MapEntry.java

Lines changed: 0 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -258,25 +258,6 @@ int encodeRefs(byte[] bs, int pos) {
258258
pos = valueRef.encode(bs,pos);
259259
return pos;
260260
}
261-
262-
/**
263-
* Writes a MapEntry or null content in compressed format (no count). Useful for
264-
* embedding an optional MapEntry inside a larger Encoding
265-
*
266-
* @param me MapEntry to encode
267-
* @param bs Byte array to write to
268-
* @param pos Starting position for encoding in byte array
269-
* @return Updated position after writing
270-
*/
271-
public static int encodeCompressed(MapEntry<?,?> me,byte[] bs, int pos) {
272-
if (me==null) {
273-
bs[pos++]=Tag.NULL;
274-
} else {
275-
bs[pos++]=Tag.VECTOR;
276-
pos = me.encodeRefs(bs,pos);
277-
}
278-
return pos;
279-
}
280261

281262
@Override
282263
public int estimatedEncodingSize() {

convex-core/src/test/java/convex/core/TokenomicsTest.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -109,9 +109,9 @@ public void testTransferFail() {
109109
Invoke t=Invoke.create(HERO, SEQ, Reader.read("(do (set-memory 0) (def a 0x12345678123456781234567812345678))"));
110110
ResultContext rc=runTransaction(t);
111111

112-
// memory of more than 16 bytes should be used, but not more than 100
112+
// memory of more than 16 bytes should be used, but not more than 200
113113
assertGreater(rc.memUsed,16);
114-
assertLess(rc.memUsed,100);
114+
assertLess(rc.memUsed,200);
115115

116116
assertEquals(rc.totalFees,rc.getJuiceFees()+rc.getMemoryFees());
117117

0 commit comments

Comments
 (0)