@Override
        public OffsetKeyedTreeMap.NodesIterator<T> nodesIteratorAt(int position) {
            return new OffsetKeyedTreeMap.NodesIterator<T>() {
                private boolean initial = true;
                private int index = STMUtils.binarySearchByKey(list, e -> e.offset, position, Comparator.comparingInt(x -> x));

                @Override
                public int getCurrOffset() {
                    if (this.initial) {
                        return position;
                    } else if (this.index >= 0 && this.index < list.size()) {
                        return list.get(this.index).offset;
                    } else if (this.index >= list.size()) {
                        return Integer.MAX_VALUE;
                    } else {
                        return Integer.MIN_VALUE;
                    }
                }

                @Nullable
                @Override
                public T getCurrValue() {
                    return this.index >= 0 && this.index < list.size() ? list.get(this.index).data : null;
                }

                @Override
                public boolean next() {
                    if (this.initial && this.index < 0) {
                        this.index = ~this.index;
                    } else {
                        this.index++;
                    }
                    this.initial = false;
                    return this.index < list.size();
                }

                @Override
                public boolean prev() {
                    if (this.initial && this.index < 0) {
                        this.index = ~this.index;
                    }
                    this.index--;
                    this.initial = false;
                    return this.index >= 0;
                }
            };
        }
Test scenarios to cover OffsetKeyedTreeMap data structure

orderings (M)
 - ascending
 - descending
 - random
<p>
modification scenarios (P)
 - all insertions (n)
 - all insertions, then all remove (different series proportions n,m)
 - intermixed insertions and remove (different series proportions n,m)
 - all insertions, then apply offset at existing key
 - all insertions, then apply offset at missing key
 - intermixed insertions, remove, apply offset (different series proportions n,m,p)
 - all insertions, then removeAtRange at existing key
 - all insertions, then removeAtRange offset at missing key
 - intermixed insertions, removeAtRange, apply offset (different series proportions n,m,p)
<p>
inspection scenarios (Q)
 - find existing key
 - find missing key
 - find existing key and iterate forward/backward till the end/head
 - find missing key and iterate forward/backward till the end/head
 - random backward-forward iterations
<p>
test/org.jkiss.dbeaver.model.lsm.test/src/org/jkiss/dbeaver/model/lsm/test/OffsetKeyedTreeMapTest.java