blob: 1b7c8167ee43090512b8c425ced15a3d6ad7bd8e [file] [log] [blame]
/*
* Copyright (c) 2010-2013, 2016 Eike Stepper (Loehne, Germany) and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Simon McDuff - initial API and implementation
* Ibrahim Sallam - code refactoring for CDO 3.0
*/
package org.eclipse.emf.cdo.server.internal.objectivity.schema;
import com.objy.as.app.Class_Object;
import com.objy.as.app.Numeric_Value;
import com.objy.as.app.VArray_Object;
import com.objy.db.app.ooId;
/**
* @author Simon McDuff
*/
public abstract class ObjyArrayList<T>
{
static final String sizeName = "elementCount";
static final String arrayName = "curr";
protected Class_Object classObject;
private VArray_Object vArray;
protected transient long cacheSize;
transient long position;
public static void initObject(Class_Object classObject)
{
// set the size to 0;
classObject.nset_numeric(sizeName, new Numeric_Value(0));
}
public ObjyArrayList(Class_Object classObject)
{
this.classObject = classObject;
this.cacheSize = -1;
}
public ooId getID()
{
return classObject.objectID();
}
// /**
// * TODO - verify need.
// */
// private Class_Object getClassObject()
// {
// return classObject;
// }
public void clear()
{
getVArray().resize(0);
cacheSize = 0;
saveSize();
}
private void shiftRight(int index)
{
shiftRight(index, 1);
}
private void shiftRight(int index, int sizeToShift)
{
long size = this.cachedSize();
for (long i = size - 1; i >= index; i--)
{
setValue(i + sizeToShift, getValue(i));
}
cacheSize += sizeToShift;
saveSize();
}
private void shiftLeft(int index)
{
long size = this.cachedSize();
for (long i = index; i < size - 1; i++)
{
setValue(i, getValue(i + 1));
}
cacheSize--;
saveSize();
}
/**
*
*/
protected void grow(int item)
{
getVArray().resize(getVArraySize() + Math.max(item + 10, 10));
}
/**
*
*/
private void prepareToInsert(int numberToAdd)
{
long size = cachedSize();
update();
if (size + numberToAdd > getVArraySize())
{
grow(numberToAdd);
}
}
protected long getVArraySize()
{
return getVArray().size();
}
protected void update()
{
getVArray().update();
}
protected VArray_Object getVArray()
{
if (vArray == null)
{
vArray = classObject.nget_varray(arrayName);
}
return vArray;
}
public void add(int index, T newValue)
{
prepareToInsert(1);
shiftRight(index);
basicSet(index, newValue);
}
public void addAll(int index, Object[] newValue)
{
prepareToInsert(newValue.length);
shiftRight(index, newValue.length);
for (int i = 0; i < newValue.length; i++)
{
@SuppressWarnings("unchecked")
T value = (T)newValue[i];
basicSet(index + i, value);
}
}
public void remove(int index)
{
shiftLeft(index);
}
public void add(T newValue)
{
long size = cachedSize();
prepareToInsert(1);
setValue(size, newValue);
cacheSize++;
saveSize();
}
public void set(long index, T newValue)
{
basicSet(index, newValue);
// cacheSize = -1;
}
public void move(long newPosition, long oldPosition)
{
if (oldPosition == newPosition)
{
return;
}
// get the object at oldPosition.
T value = getValue(oldPosition);
// remove the oldPosition.
remove((int)oldPosition);
// make a space at the newPosition by shifting elements
shiftRight((int)newPosition);
set(newPosition, value);
}
protected void basicSet(long index, T newValue)
{
if (index >= cachedSize())
{
throw new ArrayIndexOutOfBoundsException();
}
update();
setValue(index, newValue);
}
public T get(long index)
{
if (index >= size())
{
throw new ArrayIndexOutOfBoundsException();
}
return getValue(index);
}
protected abstract void setValue(long index, T newValue);
protected abstract T getValue(long index);
protected void saveSize()
{
// System.out.println(">>> classObject: " + classObject.objectID().getStoreString() + " <<<");
// System.out.println("ooArrayList.saveSize() - value to store in objy is: " + cacheSize);
classObject.nset_numeric(sizeName, new Numeric_Value(cacheSize));
resetCachedSize();
}
protected void resetCachedSize()
{
cacheSize = -1;
}
protected long cachedSize()
{
if (cacheSize == -1)
{
cacheSize = classObject.nget_numeric(sizeName).longValue();
// System.out.println(">>> classObject: " + classObject.objectID().getStoreString() + " <<<");
// System.out.println("ooArrayList.privateSize() - cacheSize was -1, value from objy is: " + cacheSize);
}
return cacheSize;
}
public long size()
{
// System.out.println(">>> classObject: " + classObject.objectID().getStoreString() + " <<<");
// Numeric_Value nValue = classObject.nget_numeric(sizeName);
// System.out.println("ooArrayList.size() - nValue: " + nValue.toString());
// return classObject.nget_numeric(sizeName).longValue();
return cachedSize();
}
}