
net.algart.arrays.PArray Maven / Gradle / Ivy
Show all versions of algart Show documentation
/*
* The MIT License (MIT)
*
* Copyright (c) 2007-2024 Daniel Alievsky, AlgART Laboratory (http://algart.net)
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
package net.algart.arrays;
import java.util.Objects;
/**
* AlgART array of primitive elements (boolean, char, byte, short, int, long, float or double),
* read-only access.
*
* Any class implementing this interface must implement one of
* {@link BitArray}, {@link CharArray},
* {@link ByteArray}, {@link ShortArray},
* {@link IntArray}, {@link LongArray},
* {@link FloatArray}, {@link DoubleArray}
* subinterfaces.
*
* @author Daniel Alievsky
*/
public interface PArray extends Array {
/**
* Return the number of memory bits occupied by every element of this array.
* The amount of memory used by the array can be estimated as
* {@link #capacity()}*bitsPerElement()/8
bytes
* (when the array capacity is large enough).
*
* If the number of occupied bits is not defined (for example, may depend on JVM implementation),
* this method returns -1.
*
*
For implementations from this package, this method returns:
* - 1 for {@link BitArray} (the value of {@link Arrays#BITS_PER_BIT} constant),
* - 16 for {@link CharArray} (the value of {@link Arrays#BITS_PER_CHAR} constant),
* - 8 for {@link ByteArray} (the value of {@link Arrays#BITS_PER_BYTE} constant),
* - 16 for {@link ShortArray} (the value of {@link Arrays#BITS_PER_SHORT} constant),
* - 32 for {@link IntArray} (the value of {@link Arrays#BITS_PER_INT} constant),
* - 64 for {@link LongArray} (the value of {@link Arrays#BITS_PER_LONG} constant),
* - 32 for {@link FloatArray} (the value of {@link Arrays#BITS_PER_FLOAT} constant),
* - 64 for {@link DoubleArray} (the value of {@link Arrays#BITS_PER_DOUBLE} constant).
*
* (-1 result is never returned by implementations from this package.)
*
*
Please keep in mind that the real amount of occupied memory, theoretically, can differ
* from the value returned by this method.
* For example, some JVM, theoretically, may store byte
elements of byte[]
array
* in 32-bit memory words. In this case, this method will return invalid result for byte arrays
* created by the {@link SimpleMemoryModel simple memory model}.
* However: we guarantee the results of this method are always correct for arrays created
* by the {@link BufferMemoryModel buffer memory model} and {@link LargeMemoryModel large memory model}.
*
*
There is a guarantee that this method works very quickly
* (usually it just returns a constant or a value of some private field).
*
* @return the number of bytes occupied by every element of this array, or -1 if it cannot be determined.
* @see Arrays#bitsPerElement(Class)
*/
long bitsPerElement();
/**
* Returns 0 for {@link BitArray}, {@link ByteArray}, {@link CharArray} and {@link ShortArray},
* Integer.MIN_VALUE
for {@link IntArray},
* Long.MIN_VALUE
for {@link LongArray},
* valueForFloatingPoint
for {@link FloatArray} and {@link DoubleArray}.
* For {@link PFixedArray fixed-point arrays} it is the minimal possible value,
* that can stored in elements of this array
* (byte
and short
elements are interpreted as unsigned).
* This method is equivalent to
* {@link Arrays#minPossibleValue(Class, double) minPossibleValue}(thisArray.getClass(),
* valueForFloatingPoint)
.
*
* @param valueForFloatingPoint the value returned for floating-point array type.
* @return the minimal possible value, that can stored in elements of this array,
* if it is a fixed-point array, or the argument for floating-point arrays.
* @see PFixedArray#minPossibleValue()
*/
double minPossibleValue(double valueForFloatingPoint);
/**
* Returns 1 for {@link BitArray},
* 0xFF for {@link ByteArray},
* 0xFFFF for {@link CharArray} and {@link ShortArray},
* Integer.MAX_VALUE
for {@link IntArray},
* Long.MAX_VALUE
for {@link LongArray},
* valueForFloatingPoint
for {@link FloatArray} and {@link DoubleArray}.
* For {@link PFixedArray fixed-point arrays} it is the maximal possible value,
* that can stored in elements of this array
* (byte
and short
elements are interpreted as unsigned).
* This method is equivalent to
* {@link Arrays#maxPossibleValue(Class, double) maxPossibleValue}(thisArray.getClass(),
* valueForFloatingPoint)
.
*
* @param valueForFloatingPoint the value returned for floating-point array type.
* @return the maximal possible value, that can stored in elements of this array,
* if it is a fixed-point array, or the argument for floating-point arrays.
* @see PFixedArray#maxPossibleValue()
*/
double maxPossibleValue(double valueForFloatingPoint);
/**
* Returns the element #index
converted to double
:
* (double)(value&0xFF)
for byte
value,
* (double)(value&0xFFFF)
for short
value,
* (double)value
for int
, long
,
* float
, double
, char
values,
* or value?1.0:0.0
for boolean
values.
* Please note that this method returns unsigned values for byte and short arrays.
* Returned value contains full information stored in the element,
* excepting the case of very large long
elements.
*
* @param index index of element to get.
* @return the element at the specified position in this array.
* @throws IndexOutOfBoundsException if index out of range 0..length()-1
.
* @see UpdatablePArray#setDouble(long, double)
*/
double getDouble(long index);
/**
* Returns the minimal index k
, so that
* lowIndex<=k<min(highIndex,thisArray.{@link #length() length()})
* and {@link #getDouble(long) getDouble}(k)==value
,
* or -1
if there is no such array element.
*
*
In particular, if lowIndex>=thisArray.{@link #length() length()}}
* or lowIndex>=highIndex
, this method returns -1
,
* and if lowIndex<0
, the result is the same as if lowIndex==0
.
*
*
You may specify lowIndex=0
and highIndex=Long.MAX_VALUE
to search
* through all array elements.
*
* @param lowIndex the low index in the array for search (inclusive).
* @param highIndex the high index in the array for search (exclusive).
* @param value the value to be found.
* @return the index of the first occurrence of this value in this array
* in range lowIndex<=index<highIndex
,
* or -1
if this value does not occur in this range.
*/
long indexOf(long lowIndex, long highIndex, double value);
/**
* Returns the maximal index k
, so that highIndex>k>=max(lowIndex,0)
* and {@link #getDouble(long) getDouble}(k)==value
,
* or -1
if there is no such array element.
*
*
In particular, if highIndex<=0
or highIndex<=lowIndex
,
* this method returns -1
,
* and if highIndex>=thisArray.{@link #length() length()}
,
* the result is the same as if highIndex==thisArray.{@link #length() length()}
.
*
*
You may specify lowIndex=0
and highIndex=Long.MAX_VALUE
to search
* through all array elements.
*
* @param lowIndex the low index in the array for search (inclusive).
* @param highIndex the high index in the array for search (exclusive).
* @param value the value to be found.
* @return the index of the last occurrence of this value in this array
* in range lowIndex<=index<highIndex
,
* or -1
if this value does not occur in this range.
*/
long lastIndexOf(long lowIndex, long highIndex, double value);
/**
* Returns true
if all elements of this array are zero
* (false
for boolean[]
array, (char)0
for char[]
).
* Returns false
if at least one of elements of this array is non-zero.
*
*
For arrays of floating-point types ({@link PFloatingArray}),
* this method considers that +0.0==-0.0
: both values are considered to be zero.
*
*
If the {@link #length() length} of this array is 0 (the array is empty), returns true
.
*
*
This method usually requires some time for execution, because it checks all array elements.
*
* @return true
if and only if all elements of this array are zero, or if this array is empty.
*/
boolean isZeroFilled();
Class extends PArray> type();
Class extends UpdatablePArray> updatableType();
Class extends MutablePArray> mutableType();
PArray asImmutable();
PArray asTrustedImmutable();
MutablePArray mutableClone(MemoryModel memoryModel);
UpdatablePArray updatableClone(MemoryModel memoryModel);
@Override
default Matrix extends PArray> matrix(long... dim) {
return Matrices.matrix(this, dim);
}
/*Repeat() byte ==> char,,short,,int,,long,,float,,double;;
Byte ==> Char,,Short,,Int,,Long,,Float,,Double */
/**
* Equivalent to the following expression:
* thisObject instanceof ByteArray a ? a.{@link ByteArray#ja()
* ja()} : {@link Arrays#toByteJavaArray(PArray) Arrays.toByteJavaArray}(thisObject)
.
*
*
This method may be used instead of {@link Arrays#toByteJavaArray(PArray)},
* if you need maximally quick access to this data in a form of byte[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard byte[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to byte
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaByte()
*/
default byte[] jaByte() {
return this instanceof ByteArray a ? a.ja() : Arrays.toByteJavaArray(this);
}/*Repeat.AutoGeneratedStart !! Auto-generated: NOT EDIT !! */
/**
* Equivalent to the following expression:
* thisObject instanceof CharArray a ? a.{@link CharArray#ja()
* ja()} : {@link Arrays#toCharJavaArray(PArray) Arrays.toCharJavaArray}(thisObject)
.
*
* This method may be used instead of {@link Arrays#toCharJavaArray(PArray)},
* if you need maximally quick access to this data in a form of char[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard char[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to char
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaChar()
*/
default char[] jaChar() {
return this instanceof CharArray a ? a.ja() : Arrays.toCharJavaArray(this);
}
/**
* Equivalent to the following expression:
* thisObject instanceof ShortArray a ? a.{@link ShortArray#ja()
* ja()} : {@link Arrays#toShortJavaArray(PArray) Arrays.toShortJavaArray}(thisObject)
.
*
* This method may be used instead of {@link Arrays#toShortJavaArray(PArray)},
* if you need maximally quick access to this data in a form of short[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard short[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to short
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaShort()
*/
default short[] jaShort() {
return this instanceof ShortArray a ? a.ja() : Arrays.toShortJavaArray(this);
}
/**
* Equivalent to the following expression:
* thisObject instanceof IntArray a ? a.{@link IntArray#ja()
* ja()} : {@link Arrays#toIntJavaArray(PArray) Arrays.toIntJavaArray}(thisObject)
.
*
* This method may be used instead of {@link Arrays#toIntJavaArray(PArray)},
* if you need maximally quick access to this data in a form of int[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard int[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to int
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaInt()
*/
default int[] jaInt() {
return this instanceof IntArray a ? a.ja() : Arrays.toIntJavaArray(this);
}
/**
* Equivalent to the following expression:
* thisObject instanceof LongArray a ? a.{@link LongArray#ja()
* ja()} : {@link Arrays#toLongJavaArray(PArray) Arrays.toLongJavaArray}(thisObject)
.
*
* This method may be used instead of {@link Arrays#toLongJavaArray(PArray)},
* if you need maximally quick access to this data in a form of long[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard long[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to long
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaLong()
*/
default long[] jaLong() {
return this instanceof LongArray a ? a.ja() : Arrays.toLongJavaArray(this);
}
/**
* Equivalent to the following expression:
* thisObject instanceof FloatArray a ? a.{@link FloatArray#ja()
* ja()} : {@link Arrays#toFloatJavaArray(PArray) Arrays.toFloatJavaArray}(thisObject)
.
*
* This method may be used instead of {@link Arrays#toFloatJavaArray(PArray)},
* if you need maximally quick access to this data in a form of float[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard float[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to float
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaFloat()
*/
default float[] jaFloat() {
return this instanceof FloatArray a ? a.ja() : Arrays.toFloatJavaArray(this);
}
/**
* Equivalent to the following expression:
* thisObject instanceof DoubleArray a ? a.{@link DoubleArray#ja()
* ja()} : {@link Arrays#toDoubleJavaArray(PArray) Arrays.toDoubleJavaArray}(thisObject)
.
*
* This method may be used instead of {@link Arrays#toDoubleJavaArray(PArray)},
* if you need maximally quick access to this data in a form of double[]
array
* and there is high probability that this AlgART array is a {@link Array#isJavaArrayWrapper() wrapper}
* for standard double[]
array.
*
* Be careful: this method can potentially lead to bugs while inaccurate usage.
* The main purpose of this method is to quickly access array data for reading.
* But it also allows you to modify this data,
* and the result of such modification is unpredictable: this may change the original AlgART array,
* but may also not change. Typically you should not attempt to modify the Java array returned by this method;
* this helps to avoid difficult bugs.
*
* @return Java array containing all the elements in this array, cast to double
type
* according to AlgART rules.
* @throws TooLargeArrayException if the array length is greater than Integer.MAX_VALUE
.
* @see Matrix#jaDouble()
*/
default double[] jaDouble() {
return this instanceof DoubleArray a ? a.ja() : Arrays.toDoubleJavaArray(this);
}/*Repeat.AutoGeneratedEnd*/
/**
* Equivalent to (UpdatablePArray) {@link MemoryModel#newUnresizableArray(Class, long)
* memoryModel.newUnresizableArray(elementType, length)}
, but with throwing
* IllegalArgumentException
in a case when the type casting to {@link UpdatablePArray}
* is impossible (non-primitive element type).
*
* @param memoryModel the memory model, used for allocation new array.
* @param elementType the type of array elements.
* @param length the length and capacity of the array.
* @return created unresizable AlgART array.
* @throws NullPointerException if one of the arguments is {@code null}.
* @throws IllegalArgumentException if elementType
is not a primitive class,
* or if the specified length is negative.
* @throws UnsupportedElementTypeException if elementType
is not supported by this memory model.
* @throws TooLargeArrayException if the specified length is too large for this memory model.
*/
static UpdatablePArray newArray(MemoryModel memoryModel, Class> elementType, long length) {
Objects.requireNonNull(memoryModel, "Null memory model");
Objects.requireNonNull(elementType, "Null element type");
if (!elementType.isPrimitive()) {
throw new IllegalArgumentException("Not a primitive type: " + elementType);
}
return (UpdatablePArray) memoryModel.newUnresizableArray(elementType, length);
}
/**
* Equivalent to {@link #newArray(MemoryModel, Class, long)
* newArray}({@link Arrays#SMM Arrays.SMM}, elementType, length)
.
*
* @param elementType the type of array elements.
* @param length the length and capacity of the array.
* @return created unresizable AlgART array.
* @throws NullPointerException if one of the arguments is {@code null}.
* @throws IllegalArgumentException if elementType
is not a primitive class,
* or if the specified length is negative.
* @throws TooLargeArrayException if the specified length is too large for {@link SimpleMemoryModel}.
*/
static UpdatablePArray newArray(Class> elementType, long length) {
return newArray(Arrays.SMM, elementType, length);
}
/**
* Equivalent to {@link SimpleMemoryModel#asUpdatablePArray(Object)
* SimpleMemoryModel.asUpdatablePArray}(array)
.
*
* @param array the source Java array.
* @return an unresizable AlgART array backed by the specified Java array.
* @throws NullPointerException if array
argument is {@code null}.
* @throws IllegalArgumentException if array
argument is not an array,
* or boolean[]
array, or Objects[]
array.
*/
static UpdatablePArray as(Object array) {
return SimpleMemoryModel.asUpdatablePArray(array);
}
}