All Downloads are FREE. Search and download functionalities are using the official Maven repository.

io.permazen.core.IndexMap Maven / Gradle / Ivy


/*
 * Copyright (C) 2015 Archie L. Cobbs. All rights reserved.
 */

package io.permazen.core;

import io.permazen.index.Index;
import io.permazen.index.Index2;
import io.permazen.index.Index3;
import io.permazen.kv.KVPair;
import io.permazen.kv.KVStore;
import io.permazen.kv.KeyFilter;
import io.permazen.kv.KeyRange;
import io.permazen.util.Bounds;
import io.permazen.util.ByteReader;
import io.permazen.util.ByteUtil;

import java.util.NavigableMap;
import java.util.NavigableSet;

/**
 * Support superclass for the various {@link NavigableMap} views of indexes.
 */
abstract class IndexMap extends FieldTypeMap {

    // Primary constructor
    private IndexMap(KVStore kv, FieldType keyType, byte[] prefix) {
        super(kv, keyType, true, prefix);
    }

    // Internal constructor
    private IndexMap(KVStore kv, FieldType keyType, boolean reversed,
      byte[] prefix, KeyRange keyRange, KeyFilter keyFilter, Bounds bounds) {
        super(kv, keyType, true, reversed, prefix, keyRange, keyFilter, bounds);
    }

    public String getDescription() {
        return "IndexMap"
          + "[prefix=" + ByteUtil.toString(this.prefix)
          + ",keyType=" + this.keyFieldType
          + (this.bounds != null ? ",bounds=" + this.bounds : "")
          + (this.keyRange != null ? ",keyRange=" + this.keyRange : "")
          + (this.keyFilter != null ? ",keyFilter=" + this.keyFilter : "")
          + (this.reversed ? ",reversed" : "")
          + "]";
    }

// AbstractKVNavigableMap

    @Override
    public IndexMap filterKeys(KeyFilter keyFilter) {
        return (IndexMap)super.filterKeys(keyFilter);
    }

    @Override
    protected V decodeValue(KVPair pair) {
        final ByteReader reader = new ByteReader(pair.getKey());
        assert ByteUtil.isPrefixOf(this.prefix, reader.getBytes());
        reader.skip(this.prefix.length);
        this.keyFieldType.skip(reader);
        return this.decodeValue(reader.getBytes(0, reader.getOffset()));
    }

    /**
     * Decode index map value.
     *
     * @param keyPrefix the portion of the {@code byte[]} key encoding the corresponding map key
     */
    protected abstract V decodeValue(byte[] keyPrefix);

// OfValues

    /**
     * Implements {@link NavigableMap} views of indexes where the map values are {@link NavigableSet}s of target values.
     */
    static class OfValues extends IndexMap> {

        private final IndexView indexView;

        // Primary constructor
        OfValues(KVStore kv, IndexView indexView) {
            super(kv, indexView.getValueType(), indexView.prefix);
            this.indexView = indexView;
        }

        // Internal constructor
        private OfValues(KVStore kv, IndexView indexView,
          boolean reversed, KeyRange keyRange, KeyFilter keyFilter, Bounds bounds) {
            super(kv, indexView.getValueType(), reversed, indexView.prefix, keyRange, keyFilter, bounds);
            this.indexView = indexView;
        }

    // AbstractKVNavigableMap

        @Override
        protected NavigableMap> createSubMap(boolean newReversed,
          KeyRange newKeyRange, KeyFilter newKeyFilter, Bounds newBounds) {
            return new OfValues<>(this.kv, this.indexView, newReversed, newKeyRange, newKeyFilter, newBounds);
        }

    // IndexMap

        @Override
        protected NavigableSet decodeValue(byte[] keyPrefix) {
            IndexSet indexSet = new IndexSet<>(this.kv, this.indexView.getTargetType(), this.indexView.prefixMode, keyPrefix);
            final KeyFilter targetFilter = this.indexView.getFilter(1);
            if (targetFilter != null) {
                indexSet = indexSet.filterKeys(new IndexKeyFilter(this.kv, keyPrefix,
                  new FieldType[] { this.indexView.getTargetType() }, new KeyFilter[] { targetFilter }, 1));
            }
            return indexSet;
        }
    }

// OfIndex

    /**
     * Implements {@link NavigableMap} views of composite indexes where the map values are of type {@link CoreIndex}.
     */
    static class OfIndex extends IndexMap> {

        private final Index2View indexView;

        // Primary constructor
        OfIndex(KVStore kv, Index2View indexView) {
            super(kv, indexView.getValue1Type(), indexView.prefix);
            this.indexView = indexView;
        }

        // Internal constructor
        private OfIndex(KVStore kv, Index2View indexView,
          boolean reversed, KeyRange keyRange, KeyFilter keyFilter, Bounds bounds) {
            super(kv, indexView.getValue1Type(), reversed, indexView.prefix, keyRange, keyFilter, bounds);
            this.indexView = indexView;
        }

    // AbstractKVNavigableMap

        @Override
        protected NavigableMap> createSubMap(boolean newReversed,
          KeyRange newKeyRange, KeyFilter newKeyFilter, Bounds newBounds) {
            return new OfIndex<>(this.kv, this.indexView, newReversed, newKeyRange, newKeyFilter, newBounds);
        }

    // IndexMap

        @Override
        protected CoreIndex decodeValue(byte[] keyPrefix) {
            return new CoreIndex<>(this.kv, this.indexView.asIndexView(keyPrefix));
        }
    }

// OfIndex2

    /**
     * Implements {@link NavigableMap} views of composite indexes where the map values are of type {@link CoreIndex2}.
     */
    static class OfIndex2 extends IndexMap> {

        private final Index3View indexView;

        // Primary constructor
        OfIndex2(KVStore kv, Index3View indexView) {
            super(kv, indexView.getValue1Type(), indexView.prefix);
            this.indexView = indexView;
        }

        // Internal constructor
        private OfIndex2(KVStore kv, Index3View indexView,
          boolean reversed, KeyRange keyRange, KeyFilter keyFilter, Bounds bounds) {
            super(kv, indexView.getValue1Type(), reversed, indexView.prefix, keyRange, keyFilter, bounds);
            this.indexView = indexView;
        }

    // AbstractKVNavigableMap

        @Override
        protected NavigableMap> createSubMap(boolean newReversed,
          KeyRange newKeyRange, KeyFilter newKeyFilter, Bounds newBounds) {
            return new OfIndex2<>(this.kv, this.indexView, newReversed, newKeyRange, newKeyFilter, newBounds);
        }

    // IndexMap

        @Override
        protected CoreIndex2 decodeValue(byte[] keyPrefix) {
            return new CoreIndex2<>(this.kv, this.indexView.asIndex2View(keyPrefix));
        }
    }

// OfIndex3

    /**
     * Implements {@link NavigableMap} views of composite indexes where the map values are of type {@link CoreIndex3}.
     */
    static class OfIndex3 extends IndexMap> {

        private final Index4View indexView;

        // Primary constructor
        OfIndex3(KVStore kv, Index4View indexView) {
            super(kv, indexView.getValue1Type(), indexView.prefix);
            this.indexView = indexView;
        }

        // Internal constructor
        private OfIndex3(KVStore kv, Index4View indexView,
          boolean reversed, KeyRange keyRange, KeyFilter keyFilter, Bounds bounds) {
            super(kv, indexView.getValue1Type(), reversed, indexView.prefix, keyRange, keyFilter, bounds);
            this.indexView = indexView;
        }

    // AbstractKVNavigableMap

        @Override
        protected NavigableMap> createSubMap(boolean newReversed,
          KeyRange newKeyRange, KeyFilter newKeyFilter, Bounds newBounds) {
            return new OfIndex3<>(this.kv, this.indexView, newReversed, newKeyRange, newKeyFilter, newBounds);
        }

    // IndexMap

        @Override
        protected CoreIndex3 decodeValue(byte[] keyPrefix) {
            return new CoreIndex3<>(this.kv, this.indexView.asIndex3View(keyPrefix));
        }
    }
}





© 2015 - 2025 Weber Informatics LLC | Privacy Policy