/*=============================================================================#
 # Copyright (c) 2009, 2020 Stephan Wahlbrink and others.
 # 
 # This program and the accompanying materials are made available under the
 # terms of the Eclipse Public License 2.0 which is available at
 # https://www.eclipse.org/legal/epl-2.0, or the Apache License, Version 2.0
 # which is available at https://www.apache.org/licenses/LICENSE-2.0.
 # 
 # SPDX-License-Identifier: EPL-2.0 OR Apache-2.0
 # 
 # Contributors:
 #     Stephan Wahlbrink <sw@wahlbrink.eu> - initial API and implementation
 #=============================================================================*/

package org.eclipse.statet.rj.data;


/**
 * This is the abstract one-dimensional data store for an R data type.
 * <p>
 * Data stores are not directly R objects but are used in the data objects
 * {@link RVector} and {@link RArray}.</p>
 * <p>
 * There are store types for each atomic type of R (namely the types/modes
 * numeric, complex, logical, character and raw) and a special
 * type for factors.  To get the type of a RStore the method {@link #getStoreType()}
 * should be used.  The available data types are:</p>
 * <ul>
 *   <li>{@link #LOGICAL}</li>
 *   <li>{@link #INTEGER}</li>
 *   <li>{@link #NUMERIC}</li>
 *   <li>{@link #COMPLEX}</li>
 *   <li>{@link #CHARACTER}</li>
 *   <li>{@link #RAW}</li>
 *   <li>{@link #FACTOR}</li>
 * </ul>
 * <p>
 * The Java value can be accessed by the getter methods for the different
 * data types.  The indexes are zero-based like in Java and not one-base like in R.
 * Because Java doesn't provide NA for primitive data types directly,
 * the data store provides the methods {@link #isNA(int)} and {@link #setNA(int)}
 * to detect and set such values.
 * If the value at an index of the store is NA, the return value of the other getter
 * methods is undefined.</p>
 * <p>
 * Indexes are zero-based (as usual in Java) and not one-base like in R.</p>
 */
public interface RStore<P> {
	
	
	/**
	 * Constant indicating a store for R data type <code>logical<code>.
	 * 
	 * <p>The story object is an instance of {@link RLogicalStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_LOGICAL logical}</code>.</p>
	 * 
	 * @see #getLogi(int)
	 * @see #setLogi(int, boolean)
	 */
	byte LOGICAL=         0x00000001;
	
	/**
	 * Constant indicating a store for R data type <code>integer<code>.
	 * 
	 * <p>The story object is an instance of {@link RIntegerStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_INTEGER integer}</code>.</p>
	 * 
	 * @see #getInt(int)
	 * @see #setInt(int, int)
	 */
	byte INTEGER=         0x00000002;
	
	/**
	 * Constant indicating a store for R data type <code>logical<code>.
	 * 
	 * <p>The story object is an instance of {@link RNumericStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_NUMERIC numeric}</code>.</p>
	 * 
	 * @see #getNum(int)
	 * @see #setNum(int, double)
	 */
	byte NUMERIC=         0x00000003;
	
	/**
	 * Constant indicating a store for R data type <code>complex<code>.
	 * 
	 * <p>The story object is an instance of {@link RComplexStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_COMPLEX complex}</code>.</p>
	 * 
	 * @see #getCplxRe(int)
	 * @see #getCplxIm(int)
	 * @see #setCplx(int, double, double)
	 */
	byte COMPLEX=         0x00000004;
	
	/**
	 * Constant indicating a store for R data type <code>character<code>.
	 * 
	 * <p>The story object is an instance of {@link RCharacterStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_CHARACTER character}</code>.</p>
	 * 
	 * @see #getChar(int)
	 * @see #setChar(int, String)
	 */
	byte CHARACTER=       0x00000005;
	
	/**
	 * Constant indicating a store for R data type <code>raw<code>.
	 * 
	 * <p>Note that raw data doesn't support NAs.</p>
	 * 
	 * <p>The story object is an instance of {@link RRawStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_RAW raw}</code>.</p>
	 * 
	 * @see #getRaw(int)
	 * @see #setRaw(int, byte)
	 */
	byte RAW=             0x00000006;
	
	/**
	 * Constant indicating a special store extending the integer
	 * data type for R objects extending the R class <code>factor<code>.
	 * 
	 * <p>The story object is an instance of {@link RFactorStore}.
	 * The {@link #getBaseVectorRClassName() class name} is
	 * <code>{@link RObject#CLASSNAME_FACTOR factor}</code> or
	 * <code>{@link RObject#CLASSNAME_ORDERED ordered}</code>.
	 * 
	 * @see RFactorStore#getInt(int)
	 * @see RFactorStore#getChar(int)
	 * @see RFactorStore#setInt(int, int)
	 * @see RFactorStore#setChar(int, String)
	 **/
	byte FACTOR=          0x0000000a;
	
	
	/**
	 * Returns the constant indicating the type of this RStore.
	 * 
	 * @return one of the constant defined in the {@link RStore} interface
	 */
	byte getStoreType();
	
	/**
	 * Returns the R class name a vector with this data store and no other
	 * class definitions will have.
	 * 
	 * @return the class name
	 */
	String getBaseVectorRClassName();
	
	/**
	 * Returns the length of this data store.
	 * 
	 * <p>If this is a data store dummy for structure only R objects in Java
	 * ({@link RObjectFactory#F_ONLY_STRUCT}), the value is <code>-1</code>.
	 * 
	 * @return the length or <code>-1</code>
	 */
	long getLength();
	
	/**
	 * Tests if the value at the specified index is NA.
	 * <p>
	 * Note that the analogous method to the R function <code>is.na(x)</code>
	 * is {@link #isMissing(int)}; this method returns <code>false</code> for NaN values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return <code>true</code>, if the value at the specified index is NA, otherwise <code>false</code>
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	boolean isNA(int idx);
	
	/**
	 * Tests if the value at the specified index is NA.
	 * <p>
	 * Note that the analogous method to the R function <code>is.na(x)</code>
	 * is {@link #isMissing(int)}; this method returns <code>false</code> for NaN values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return <code>true</code>, if the value at the specified index is NA, otherwise <code>false</code>
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	boolean isNA(long idx);
	
	/**
	 * Tests if the value at the specified index is NA <b>or</b> NaN (if supported by data type).
	 * It works by analogy with the R function <code>is.na(x)</code>.
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return <code>true</code>, if the value at the specified index is NA or NaN, otherwise <code>false</code>
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	boolean isMissing(int idx);
	
	/**
	 * Tests if the value at the specified index is NA <b>or</b> NaN (if supported by data type).
	 * It works by analogy with the R function <code>is.na(x)</code>.
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return <code>true</code>, if the value at the specified index is NA or NaN, otherwise <code>false</code>
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	boolean isMissing(long idx);
	
	/**
	 * Sets the value at the specified index to NA.
	 * <p>
	 * Note that raw doesn't support NAs.</p>.
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param idx the index of the value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setNA(int idx);
	
	/**
	 * Sets the value at the specified index to NA.
	 * <p>
	 * Note that raw doesn't support NAs.</p>.
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param idx the index of the value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setNA(long idx);
	
	/**
	 * Return the logical/boolean value at the specified index.
	 * <p>
	 * Logical values in R matches exactly the Java boolean values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current logical value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	boolean getLogi(int idx);
	
	/**
	 * Return the logical/boolean value at the specified index.
	 * <p>
	 * Logical values in R matches exactly the Java boolean values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current logical value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	boolean getLogi(long idx);
	
	/**
	 * Sets the logical/boolean value at the specified index.
	 * <p>
	 * Logical values in R matches exactly the Java boolean values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param logical the logical value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setLogi(int idx, boolean logical);
	
	/**
	 * Sets the logical/boolean value at the specified index.
	 * <p>
	 * Logical values in R matches exactly the Java boolean values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param logical the logical value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setLogi(long idx, boolean logical);
	
	/**
	 * Return the integer/int value at the specified index.
	 * <p>
	 * Integer values in R matches exactly the Java int values, except
	 * {@link Integer#MIN_VALUE} which doesn't exists in R and is mapped to NA.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current integer value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	int getInt(int idx);
	
	/**
	 * Return the integer/int value at the specified index.
	 * <p>
	 * Integer values in R matches exactly the Java int values, except
	 * {@link Integer#MIN_VALUE} which doesn't exists in R and is mapped to NA.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current integer value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	int getInt(long idx);
	
	/**
	 * Sets the integer/int value at the specified index.
	 * <p>
	 * Integer values in R matches exactly the Java int values, except
	 * {@link Integer#MIN_VALUE} which doesn't exists in R and is mapped to NA.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param integer the integer value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setInt(int idx, int integer);
	
	/**
	 * Sets the integer/int value at the specified index.
	 * <p>
	 * Integer values in R matches exactly the Java int values, except
	 * {@link Integer#MIN_VALUE} which doesn't exists in R and is mapped to NA.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param integer the integer value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setInt(long idx, int integer);
	
	/**
	 * Return the numeric/real/double value at the specified index.
	 * <p>
	 * Numeric values in R matches exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {@link Double#isNaN(double)},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current real value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	double getNum(int idx);
	
	/**
	 * Return the numeric/real/double value at the specified index.
	 * <p>
	 * Numeric values in R matches exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {@link Double#isNaN(double)},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current real value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	double getNum(long idx);
	
	/**
	 * Sets the numeric/real/double value at the specified index.
	 * <p>
	 * Numeric values in R matches exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {@link Double#NaN},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param numeric the real value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setNum(int idx, double numeric);
	
	/**
	 * Sets the numeric/real/double value at the specified index.
	 * <p>
	 * Numeric values in R matches exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {@link Double#NaN},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param numeric the real value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setNum(long idx, double numeric);
	
	/**
	 * Returns the real part the complex number value at the specified index.
	 * <p>
	 * The numeric values of the parts of the complex number in R matches
	 * exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {Double#isNaN(double)},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current real part of the complex number value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	double getCplxRe(int idx);
	
	/**
	 * Returns the real part the complex number value at the specified index.
	 * <p>
	 * The numeric values of the parts of the complex number in R matches
	 * exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {Double#isNaN(double)},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current real part of the complex number value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	double getCplxRe(long idx);
	
	/**
	 * Returns the imaginary part the complex number value at the specified index.
	 * <p>
	 * The numeric values of the parts of the complex number in R matches
	 * exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {Double#isNaN(double)},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current imaginary part of the complex number value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	double getCplxIm(int idx);
	
	/**
	 * Returns the imaginary part the complex number value at the specified index.
	 * <p>
	 * The numeric values of the parts of the complex number in R matches
	 * exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {Double#isNaN(double)},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current imaginary part of the complex number value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	double getCplxIm(long idx);
	
	/**
	 * Sets the complex number value at the specified index.
	 * <p>
	 * The numeric values of the parts of the complex number in R matches
	 * exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {@link Double#NaN},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param real the real part of the complex number value
	 * @param imaginary the imaginary part of the complex number value
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setCplx(int idx, double real, double imaginary);
	
	/**
	 * Sets the complex number value at the specified index.
	 * <p>
	 * The numeric values of the parts of the complex number in R matches
	 * exactly the Java double values.
	 * Also NaN, Inf and -Inf respectively {@link Double#NaN},
	 * {@link Double#POSITIVE_INFINITY} and {@link Double#NEGATIVE_INFINITY} are
	 * supported.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param real the real part of the complex number value
	 * @param imaginary the imaginary part of the complex number value
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setCplx(long idx, double real, double imaginary);
	
	/**
	 * Returns the character value at the specified index.
	 * <p>
	 * R character values matches exactly Java string values, if R supports
	 * UTF encoding.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current character value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	String getChar(int idx);
	
	/**
	 * Returns the character value at the specified index.
	 * <p>
	 * R character values matches exactly Java string values, if R supports
	 * UTF encoding.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current character value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	String getChar(long idx);
	
	/**
	 * Sets the character/String value at the specified index.
	 * <p>
	 * R character values matches exactly Java string values, if R supports
	 * UTF encoding.</p>
	 * <p>
	 * No quoting or escaping is required. Quoting or escaping the value
	 * would change the real value.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param character the character value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setChar(int idx, String character);
	
	/**
	 * Sets the character/String value at the specified index.
	 * <p>
	 * R character values matches exactly Java string values, if R supports
	 * UTF encoding.</p>
	 * <p>
	 * No quoting or escaping is required. Quoting or escaping the value
	 * would change the real value.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param character the character value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setChar(long idx, String character);
	
	/**
	 * Returns the raw/byte value at the specified index.
	 * <p>
	 * R raw values matches exactly Java byte values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current raw value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	byte getRaw(int idx);
	
	/**
	 * Returns the raw/byte value at the specified index.
	 * <p>
	 * R raw values matches exactly Java byte values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return the current raw value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	byte getRaw(long idx);
	
	/**
	 * Sets the raw/byte value at the specified index.
	 * <p>
	 * R raw values matches exactly Java byte values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param raw the raw value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setRaw(int idx, byte raw);
	
	/**
	 * Sets the raw/byte value at the specified index.
	 * <p>
	 * R raw values matches exactly Java byte values.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @param raw the raw value to set
	 * @throws UnsupportedOperationException if the store is not modifiable
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	void setRaw(long idx, byte raw);
	
	/**
	 * Returns the value at the specified index as Java object. The subtypes of
	 * RStore defines more specific array types.
	 * <p>
	 * R NA values are represented as <code>null</code>. Java primitives are converted
	 * into its wrapper classes.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return an object for the current value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	P get(int idx);
	
	/**
	 * Returns the value at the specified index as Java object. The subtypes of
	 * RStore defines more specific array types.
	 * <p>
	 * R NA values are represented as <code>null</code>. Java primitives are converted
	 * into its wrapper classes.</p>
	 * 
	 * @param idx the index (zero-based) of the value
	 * @return an object for the current value
	 * @throws IndexOutOfBoundsException if the index is out of range
	 *     (idx &lt; 0 || idx &gt;= length()).
	 */
	P get(long idx);
	
	/**
	 * Returns the values of the store as Java object array. The subtypes of
	 * RStore defines more specific array types.
	 * <p>
	 * The array is newly created for each call of this method. It has the
	 * length {@link #getLength()}. R NA values are represented as <code>null</code>
	 * in the array. Java primitives are converted into its wrapper classes.</p>
	 * 
	 * @return a object array with the values of the store
	 */
	P[] toArray();
	
	boolean allEqual(RStore<?> other);
	
	
	/**
	 * Returns if the store contains the a NA value.
	 * 
	 * @return <code>true</code> if the store contains a NA value, otherwise false
	 * 
	 * @since de.walware.rj.data 2.1
	 */
	boolean containsNA();
	
	/**
	 * Returns the index of the first NA value in the store.
	 * 
	 * @return index (zero-base) of first equal value, otherwise <code>-1</code>
	 * 
	 * @since de.walware.rj.data 2.1
	 */
	long indexOfNA();
	
	/**
	 * Returns the index of the first NA value in the store, starting from the specified index.
	 * 
	 * @param fromIdx index (zero-based) from which to start the search
	 * @return index (zero-based) of first equal value, otherwise <code>-1</code>
	 * 
	 * @since de.walware.rj.data 2.1
	 */
	long indexOfNA(long fromIdx);
	
	/**
	 * Returns if the store contains the specified integer value.
	 * 
	 * @param value the value to search for
	 * @return <code>true</code> if the store contains the value, otherwise false
	 */
	boolean contains(final int integer);
	
	/**
	 * Returns the index of the first value in the store equal to the of the specified integer
	 * value.
	 * 
	 * @param integer the value to search for
	 * @return index (zero-based) of first equal value, otherwise <code>-1</code>
	 */
	long indexOf(int integer);
	
	/**
	 * Returns the index of the first value in the store equal to the of the specified integer
	 * value, starting from the specified index.
	 * 
	 * @param integer the value to search for
	 * @param fromIdx index (zero-based) from which to start the search
	 * @return index (zero-based) of first equal value, otherwise <code>-1</code>
	 */
	long indexOf(int integer, long fromIdx);
	
	/**
	 * Returns if the store contains the specified character value.
	 * 
	 * @param value the value to search for
	 * @return <code>true</code> if the store contains the value, otherwise false
	 */
	boolean contains(final String value);
	
	/**
	 * Returns the index of the first value in the store equal to the of the specified character
	 * value.
	 * 
	 * @param character the value to search for
	 * @return index (zero-base) of first equal value, otherwise <code>-1</code>
	 */
	long indexOf(String character);
	
	/**
	 * Returns the index of the first value in the store equal to the of the specified character
	 * value, starting from the specified index.
	 * 
	 * @param character the value to search for
	 * @param fromIdx index (zero-based) from which to start the search
	 * @return index (zero-based) of first equal value, otherwise <code>-1</code>
	 */
	long indexOf(String character, long fromIdx);
	
}
