blob: 717c7b8d8f89eba791e8dd3d97f1b6a712aecca4 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/
package org.apache.sysds.runtime.compress.colgroup.indexes;
import java.io.DataInput;
import java.io.DataOutput;
import java.io.IOException;
import org.apache.sysds.runtime.compress.DMLCompressionException;
import org.apache.sysds.runtime.compress.utils.IntArrayList;
public class RangeIndex extends AColIndex {
private final int l;
private final int u; // not inclusive
public RangeIndex(int nCol) {
l = 0;
u = nCol;
}
public RangeIndex(int l, int u) {
this.l = l;
this.u = u;
}
@Override
public int size() {
return u - l;
}
@Override
public int get(int i) {
return l + i;
}
@Override
public IColIndex shift(int i) {
return new RangeIndex(l + i, u + i);
}
@Override
public void write(DataOutput out) throws IOException {
out.writeByte(ColIndexType.RANGE.ordinal());
out.writeInt(l);
out.writeInt(u);
}
public static RangeIndex read(DataInput in) throws IOException {
int l = in.readInt();
int u = in.readInt();
return new RangeIndex(l, u);
}
@Override
public long getExactSizeOnDisk() {
return 1 + 4 + 4;
}
@Override
public long estimateInMemorySize() {
return estimateInMemorySizeStatic();
}
public static long estimateInMemorySizeStatic() {
return 16 + 8;
}
@Override
public IIterate iterator() {
return new RangeIterator();
}
@Override
public int findIndex(int i) {
if(i < l)
return -1;
else if(i < u)
return i - l;
else
return -1 * u - 1 + l;
}
@Override
public SliceResult slice(int l, int u) {
if(u <= this.l)
return new SliceResult(0, 0, null);
else if(l >= this.u)
return new SliceResult(0, 0, null);
else if(l <= this.l && u >= this.u)
return new SliceResult(0, size(), new RangeIndex(this.l - l, this.u - l));
else {
int offL = Math.max(l, this.l) - this.l;
int offR = Math.min(u, this.u) - this.l;
return new SliceResult(offL, offR, new RangeIndex(Math.max(l, this.l) - l, Math.min(u, this.u) - l));
}
}
@Override
public boolean equals(IColIndex other) {
if(other instanceof RangeIndex) {
RangeIndex ot = (RangeIndex) other;
return ot.l == l && ot.u == u;
}
else
return other.equals(this);
}
@Override
public IColIndex combine(IColIndex other) {
if(other.size() == 1) {
int v = other.get(0);
if(v + 1 == l)
return new RangeIndex(l - 1, u);
else if(v == u)
return new RangeIndex(l, u + 1);
}
final int sr = other.size();
final int sl = size();
final int[] ret = new int[sr + sl];
int pl = 0;
int pr = 0;
int i = 0;
while(pl < sl && pr < sr) {
final int vl = get(pl);
final int vr = other.get(pr);
if(vl < vr) {
ret[i++] = vl;
pl++;
}
else {
ret[i++] = vr;
pr++;
}
}
while(pl < sl)
ret[i++] = get(pl++);
while(pr < sr)
ret[i++] = other.get(pr++);
return ColIndexFactory.create(ret);
}
@Override
public boolean isContiguous() {
return true;
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append(this.getClass().getSimpleName());
sb.append("[");
sb.append(l);
sb.append(" -> ");
sb.append(u);
sb.append("]");
return sb.toString();
}
protected static boolean isValidRange(int[] indexes) {
return isValidRange(indexes, indexes.length);
}
protected static boolean isValidRange(IntArrayList indexes) {
return isValidRange(indexes.extractValues(), indexes.size());
}
private static boolean isValidRange(final int[] indexes, final int length) {
int len = length;
int first = indexes[0];
int last = indexes[length - 1];
if(last - first + 1 == len) {
for(int i = 1; i < length; i++)
if(indexes[i - 1] > indexes[i])
return false;
return true;
}
else
return false;
}
@Override
public int[] getReorderingIndex() {
throw new DMLCompressionException("not valid to get reordering Index for range");
}
@Override
public boolean isSorted() {
return true;
}
@Override
public IColIndex sort() {
throw new DMLCompressionException("range is always sorted");
}
protected class RangeIterator implements IIterate {
int cl = l;
@Override
public int next() {
return cl++;
}
@Override
public boolean hasNext() {
return cl < u;
}
@Override
public int v() {
return cl;
}
@Override
public int i() {
return cl - l;
}
}
}