|
AlgART Home | ||||||||
| PREV PACKAGE NEXT PACKAGE | FRAMES NO FRAMES | ||||||||
See:
Description
| Interface Summary | |
|---|---|
| Array | AlgART array of any elements, read-only access. |
| ArrayContext | The context of processing AlgART arrays. |
| ArrayProcessor | Abstract array processor: an algorithm processing AlgART arrays or matrices. |
| ArrayProcessorWithContextSwitching | Array processor allowing to swtich the current context. |
| BitArray | AlgART array of boolean values, read-only access. |
| BitStack | Stack of boolean values. |
| ByteArray | AlgART array of byte values, read-only access. |
| ByteStack | Stack of byte values. |
| CharArray | AlgART array of char values, read-only access. |
| CharStack | Stack of char values. |
| CombinedMemoryModel.BufferedCombiner<E> | Special version of CombinedMemoryModel.Combiner interface allowing
to optimize block access to the combined array. |
| CombinedMemoryModel.Combiner<E> | This interface should be implemented to allow saving objects
in arrays created via combined memory model. |
| CombinedMemoryModel.CombinerInPlace<E> | Special version of CombinedMemoryModel.Combiner interface allowing
to load an element without creating new Java object. |
| ConnectedObjectScanner.ElementVisitor | Visitor of matrix elements. |
| DataBitBuffer | Data buffer for bit elements. |
| DataBuffer | Data buffer: an interface allowing to read and write blocks from / to some linear data storage, containing a sequence of elements of any Java type, with maximal performance. |
| DataByteBuffer | Data buffer for byte elements. |
| DataCharBuffer | Data buffer for char elements. |
| DataDoubleBuffer | Data buffer for double elements. |
| DataFile | Some "data file" (usually disk file) that supports file-mapping operation. |
| DataFile.BufferHolder | An object allowing to access mapped data, returned by the DataFile.map(net.algart.arrays.DataFile.Range, boolean) method. |
| DataFileModel<P> | Data file model: the factory allowing to create and remove some file-like objects
("data files"). |
| DataFloatBuffer | Data buffer for float elements. |
| DataIntBuffer | Data buffer for int elements. |
| DataLongBuffer | Data buffer for long elements. |
| DataObjectBuffer<E> | Data buffer for Object elements. |
| DataShortBuffer | Data buffer for short elements. |
| DirectAccessible | An object that can be viewed as a Java array or a part of Java array. |
| DoubleArray | AlgART array of double values, read-only access. |
| DoubleStack | Stack of double values. |
| FloatArray | AlgART array of float values, read-only access. |
| FloatStack | Stack of float values. |
| GeneralizedBitProcessing.SliceOperation | Algorithm of processing bit arrays, that should be generalized for another element type via
GeneralizedBitProcessing class. |
| IntArray | AlgART array of int values, read-only access. |
| IntStack | Stack of int values. |
| IterativeArrayProcessor<T> | An iterative algorithm processing some AlgART array (arrays) or matrix (matrices). |
| LongArray | AlgART array of long values, read-only access. |
| LongStack | Stack of long values. |
| Matrix<T extends Array> | AlgART matrix: multidimensional array. |
| MemoryModel | Virtual memory model: implementations of this abstract factory is the main way of creating new AlgART arrays. |
| MutableArray | AlgART one-dimensional array of any elements, full access (reading, writing, resizing). |
| MutableBitArray | Resizable AlgART array of boolean values. |
| MutableByteArray | Resizable AlgART array of byte values. |
| MutableCharArray | Resizable AlgART array of char values. |
| MutableDoubleArray | Resizable AlgART array of double values. |
| MutableFloatArray | Resizable AlgART array of float values. |
| MutableIntArray | Resizable AlgART array of int values. |
| MutableLongArray | Resizable AlgART array of long values. |
| MutableObjectArray<E> | Resizable AlgART array of some objects (non-primitive values) with the specified generic type E, read-write and resize access. |
| MutableObjectInPlaceArray<E> | Special version of MutableObjectArray allowing
to load an element without creating new Java object. |
| MutablePArray | Resizable AlgART array of primitive elements (boolean, char, byte, short, int, long, float or double). |
| MutablePFixedArray | Resizable AlgART array of any fixed-point numeric, character or bit primitive elements (byte, short, int, long, char or boolean). |
| MutablePFloatingArray | Resizable AlgART array of any floating-point primitive elements (float or double). |
| MutablePIntegerArray | Resizable AlgART array of any fixed-point numeric primitive elements (byte, short, int or long). |
| MutablePNumberArray | Resizable AlgART array of any numeric primitive elements (byte, short, int, long, float or double). |
| MutableShortArray | Resizable AlgART array of short values. |
| ObjectArray<E> | AlgART array of some objects (non-primitive values) with the specified generic type E, read-only access. |
| ObjectInPlaceArray<E> | Special version of ObjectArray allowing
to load an element without creating new Java object. |
| ObjectStack<E> | Stack of some objects (non-primitive values). |
| PArray | AlgART array of primitive elements (boolean, char, byte, short, int, long, float or double), read-only access. |
| PFixedArray | AlgART array of any fixed-point primitive numeric, character or bit elements (byte, short, int, long, char or boolean), read-only access. |
| PFloatingArray | AlgART array of any floating-point primitive elements (float or double), read-only access. |
| PIntegerArray | AlgART array of any fixed-point primitive numeric elements (byte, short, int or long), read-only access. |
| PNumberArray | AlgART array of any primitive numeric elements (byte, short, int, long, float or double), read-only access. |
| ShortArray | AlgART array of short values, read-only access. |
| ShortStack | Stack of short values. |
| Sorter.Comparator | This interface should be implemented to allow comparing sorted objects. |
| Sorter.Exchanger | This interface should be implemented to allow exchanging sorted objects. |
| Stack | Resizable stack of any elements. |
| ThreadPoolFactory | The factory allowing to get a thread pool (ExecutorService) for processing some AlgART array. |
| UpdatableArray | AlgART one-dimensional array of any elements, read/write access, no resizing. |
| UpdatableBitArray | AlgART array of boolean values, read/write access, no resizing. |
| UpdatableByteArray | AlgART array of byte values, read/write access, no resizing. |
| UpdatableCharArray | AlgART array of char values, read/write access, no resizing. |
| UpdatableDoubleArray | AlgART array of double values, read/write access, no resizing. |
| UpdatableFloatArray | AlgART array of float values, read/write access, no resizing. |
| UpdatableIntArray | AlgART array of int values, read/write access, no resizing. |
| UpdatableLongArray | AlgART array of long values, read/write access, no resizing. |
| UpdatableObjectArray<E> | AlgART array of some objects (non-primitive values) with the specified generic type E, read/write access, no resizing. |
| UpdatableObjectInPlaceArray<E> | Special version of UpdatableObjectArray allowing
to load an element without creating new Java object. |
| UpdatablePArray | AlgART array of primitive elements (boolean, char, byte, short, int, long, float or double), read/write access, no resizing. |
| UpdatablePFixedArray | AlgART array of any fixed-point primitive numeric, character or bit elements (byte, short, int, long, char or boolean), read/write access, no resizing. |
| UpdatablePFloatingArray | AlgART array of any floating-point primitive elements (float or double), read/write access, no resizing. |
| UpdatablePIntegerArray | AlgART array of any fixed-point primitive numeric elements (byte, short, int or long), read/write access, no resizing. |
| UpdatablePNumberArray | AlgART array of any primitive numeric elements (byte, short, int, long, float or double), read-only access. |
| UpdatableShortArray | AlgART array of short values, read/write access, no resizing. |
| Class Summary | |
|---|---|
| AbstractArray | Implementation of basic functions of MutableArray interface. |
| AbstractArrayContext | A skeletal implementation of the ArrayContext interface to minimize
the effort required to implement this interface. |
| AbstractArrayProcessorWithContextSwitching | A skeletal implementation of the ArrayProcessorWithContextSwitching interface. |
| AbstractBitArray | Implementation of almost all basic functions of BitArray interface. |
| AbstractByteArray | Implementation of almost all basic functions of ByteArray interface. |
| AbstractCharArray | Implementation of almost all basic functions of CharArray interface. |
| AbstractDataFileModel | A skeletal implementation of the DataFileModel interface to minimize
the effort required to implement this interface for processing usual disk files. |
| AbstractDoubleArray | Implementation of almost all basic functions of DoubleArray interface. |
| AbstractFloatArray | Implementation of almost all basic functions of FloatArray interface. |
| AbstractIntArray | Implementation of almost all basic functions of IntArray interface. |
| AbstractIterativeArrayProcessor<T> | A skeletal implementation of the IterativeArrayProcessor interface. |
| AbstractLongArray | Implementation of almost all basic functions of LongArray interface. |
| AbstractMatrix<T extends Array> | A skeletal implementation of the Matrix interface to minimize
the effort required to implement this interface. |
| AbstractMemoryModel | A skeletal implementation of the MemoryModel interface to minimize
the effort required to implement this interface. |
| AbstractObjectArray<E> | Implementation of almost all basic functions of ObjectArray interface. |
| AbstractShortArray | Implementation of almost all basic functions of ShortArray interface. |
| AbstractUpdatableBitArray | Implementation of almost all basic functions of UpdatableBitArray interface. |
| AbstractUpdatableByteArray | Implementation of almost all basic functions of UpdatableByteArray interface. |
| AbstractUpdatableCharArray | Implementation of almost all basic functions of UpdatableCharArray interface. |
| AbstractUpdatableDoubleArray | Implementation of almost all basic functions of UpdatableDoubleArray interface. |
| AbstractUpdatableFloatArray | Implementation of almost all basic functions of UpdatableFloatArray interface. |
| AbstractUpdatableIntArray | Implementation of almost all basic functions of UpdatableIntArray interface. |
| AbstractUpdatableLongArray | Implementation of almost all basic functions of UpdatableLongArray interface. |
| AbstractUpdatableObjectArray<E> | Implementation of almost all basic functions of UpdatableObjectArray interface. |
| AbstractUpdatableShortArray | Implementation of almost all basic functions of UpdatableShortArray interface. |
| ArrayContext.Event | The array processing event: an argument of ArrayContext.updateProgress(ArrayContext.Event) method. |
| ArrayPool | A simple pool of the unresizable AlgART arrays
(usually work buffers) with the same size and type of elements,
based on a list of SoftReference. |
| Arrays | A set of static methods useful for working with AlgART arrays. |
| Arrays.Copier | Implementation of Arrays.ParallelExecutor performing
simple copying of the source array. |
| Arrays.MinMaxInfo | The helper class for Arrays.rangeOf(PArray, MinMaxInfo) method, containing information
about the minimum and maximum in some AlgART array. |
| Arrays.ParallelExecutor | The class simplifying the parallel processing a large AlgART array in several threads,
where each thread process a set of ranges of the source array (Array.subArray). |
| Arrays.SystemSettings | A set of static methods for getting some important global settings,
stored in system properties and used for customizing modules procesing AlgART arrays. |
| Boundary2DScanner | 2-dimensional object boundaries scanner: the class allowing to trace boundaries of objects, "drawn" at some 2-dimensional bit matrix. |
| Boundary2DScanner.SimpleMeasurer | The wrapper, that peforms scanning boundaries via the specified parent scanner and, in addition, measures some simple parameters of every scanned boundary. |
| Boundary2DScanner.Step | The step of scanning the boundary: moving from one boundary segment to the next boundary segment. |
| Boundary2DScanner.Wrapper | Special variant of Boundary2DScanner class, that redirects all methods to some
parent scanner and, maybe, performs some additional actions. |
| BufferMemoryModel | The memory model, based on ByteBuffer and other buffers from java.nio package. |
| CombinedMemoryModel<E> | The memory model allowing to create combined arrays: special kind of AlgART arrays, that store an array of Java objects with minimal amount of memory, namely in one or several another "parallel" arrays. |
| CombinedMemoryModel.AbstractByteBufferCombiner<E> | A skeleton class allowing to simplify implementation of
CombinedMemoryModel.Combiner interface. |
| CombinedMemoryModel.AbstractByteBufferCombinerInPlace<E> | A version of CombinedMemoryModel.AbstractByteBufferCombiner skeleton class
implementing CombinedMemoryModel.CombinerInPlace interface. |
| ConnectedObjectScanner | Connected objects scanner: the class performing scanning and clearing connected objects, "drawn" on some n-dimensional updatable bit matrix. |
| DataFile.Range | Pair of 2 long values position
and length, describing the range position..position+length-1
of linear addresses in some data file. |
| DefaultDataFileModel | Default implementation of DataFileModel that creates usual Java files,
which are mapped via standard Java technique (FileChannel.map method). |
| DefaultThreadPoolFactory | A simple implementation of ThreadPoolFactory interface. |
| GeneralizedBitProcessing | Universal convertor of bitwise operation (an algorithm processing BitArray)
to operation over any primitive type (an algorithm processing PArray). |
| JArrayPool | A simple pool of the Java arrays (usually work buffers) with the same size and type of elements, based on a list of SoftReference. |
| JArrays | Some operations for Java array manipulation, in addition to java.util.Arrays. |
| JBuffers | Some operations for Java NIO buffers manipulation in the same manner as array operations from
JArrays and java.util.Arrays classes. |
| LargeMemoryModel<P> | The memory model, storing array elements in an external file. |
| Matrices | Utilities useful for working with AlgART matrices. |
| Matrices.ResizingMethod | Resizing mode for Matrices.asResized(MemoryModel, ResizingMethod, Matrix, long[]) method. |
| Matrices.ResizingMethod.Averaging | Resizing method with averaging (while compression). |
| MatrixInfo | Full structural information about the AlgART matrix, consisting of elements
of some primitive types, in a form convenient for serialization. |
| PackedBitArrays | Operations with bit arrays packed into long[] Java arrays. |
| PackedBitBuffers | Operations with bit arrays packed into java.nio.LongBuffer. |
| Percentiles | Finding percentiles. |
| SignalMemoryModel | The degenerate memory model that does not allow to create any AlgART arrays. |
| SimpleMemoryModel | The simplest memory model, based on usual Java arrays. |
| Sorter | Sorting algorithms. |
| StandardIODataFileModel | Alternative implementation of DataFileModel that creates usual Java files,
but emulates mapping via standard read/write operations
(StandardIODataFileModel.readAllBuffer(FileChannel, long, ByteBuffer) and
StandardIODataFileModel.writeAllBuffer(FileChannel, long, ByteBuffer) methods). |
| Enum Summary | |
|---|---|
| Arrays.TaskExecutionOrder | Describes when to execute the task passed to
Arrays.addShutdownTask(Runnable, TaskExecutionOrder) method. |
| Boundary2DScanner.ObjectParameter | The class describing what parameters of the connected object boundary should be measured by
Boundary2DScanner.SimpleMeasurer class. |
| Boundary2DScanner.Side | The pixel side. |
| ConnectivityType | Connectity kind of the connected object in the matrix. |
| DataBuffer.AccessMode | Access mode, describing access to data buffers. |
| DataFile.OpenResult | Possible results of DataFile.open(boolean) method. |
| Matrices.InterpolationMethod | Interpolation method for representing AlgART matrix as a mathematical function. |
| Exception Summary | |
|---|---|
| IllegalInfoSyntaxException | Checked exception thrown if the format of byte[] or String
serialized form of the MatrixInfo is invalid. |
| NoArrayException | Unchecked exception thrown by DirectAccessible.javaArray() method
if the object cannot be viewed as a Java array. |
| SizeMismatchException | Unchecked exception thrown by some methods, processing several AlgART arrays or matrices, when the passed arrays / matrices have different lengths / dimensions. |
| TooLargeArrayException | Unchecked exception thrown if the current or desired array length is extremely large. |
| UnsupportedElementTypeException | Unchecked exception thrown by methods, creating new AlgART arrays
(as MemoryModel.newEmptyArray(Class)), if the specified element type
is not supported by the memory model. |
| Error Summary | |
|---|---|
| UnallowedMutationError | Unchecked error thrown if the elements of trusted immutable
AlgART arrays have been changed. |
Defines AlgART arrays: generalized arrays of any Java types.
AlgART arrays are classes allowing to store one- or multi-dimensional random access arrays, containing elements of any Java type, including primitive types.
AlgART arrays are homogeneous: the type of elements of an array are the same (for primitive elements) or are inheritors of the same class (for non-primitive elements). AlgART arrays, unlike standard Java arrays, may be resizable: you may add elements to the array end or remove some elements at any time.
AlgART arrays include all basic functionality of the standard Java ArrayList class and of Java NIO buffers, but also provide a lot of new features.
The basic AlgART array interface is Array:
read-only one-dimensional array with any element type.
There are a lot of its subinterfaces with additional functionality and restrictions.
Matrix interface. Any one-dimensional
array can be viewed as a matrix and vice versa.
MemoryModel interface),
that provide a standard way of implementing any schemes for storing data,
from simple Java arrays to mapped disk files.
The current implementation offers 4 basic memory models:
Simple memory model,
that stores data in usual Java arrays;Buffer memory model,
that use Java NIO buffers for storing data:
it does not provide the maximal access speed, but can provide better overall performance
in applications that require large amount of RAM, and also provides good compatibility
with Java code working with channels and NIO buffers;Large memory model,
that may store large amount of primitive elements in mapped-files —
it is the only way (in current Java versions) to create very large arrays,
containing, theoretically, up to 263-1 elements;Combined memory model,
allowing efficient storing non-primitive elements in a set of another arrays
— together with LargeMemoryModel, it allows to store
more than 231-1 non-primitive elements in one array.Large memory model
is based on special low-level factories, named Data File Models
(DataFileModel interface).
Creating non-standard data file models allows to easily implement storing
array elements in almost any possible devices or storages.
For example, it's possible to create data file model that will represent a content of
BufferedImage
as AlgART array.
class Circle {
int x;
int y;
int r;
}
Unlike this, Java NIO buffers allow efficient storing only non-boolean primitive elements,
and standard ArrayList always stores every element as a separate instance,
that require a lot of extra memory for simple structures.Array),
read-write access without changing the array length
(UpdatableArray),
stack access — adding and removing the last element
(Stack),
and full access including resizing the array
(MutableArray).
In addition, there are DataBuffer interface,
providing convenient and maximally efficient block access to AlgART arrays,
and DirectAccessible interface
for quick access to internal Java array if the elements are
really stored in an underlying Java array.
There is also full set of interfaces for quick and convenient access to
elements of all primitive types.cloned
(the simplest protection),
converted to immutable form,
to more efficient (in some cases) trusted immutable form or
to special quite safe copy-on-next-write form.
Also, any resizable array can be converted to
unresizable form,
which length is fixed.
Using read-only Array or
unresizable UpdatableArray interfaces
(and their inheritors for primitive types),
instead of the full MutableArray,
also helps to avoid unwanted operations.
The basic set of AlgART array interfaces and classes can be represented as 3-dimentional structure.
The 1st dimension corresponds to the type of elements: there are separate interfaces and classes
for all 8 primitive Java types and for Object type (and its inheritors).
The 2nd dimension describes the array functionality:
read-only access (Array),
read/write access (UpdatableArray),
full access including resizing (MutableArray),
quick access to internal Java array (DirectAccessible).
The 3rd dimension is the Virtual Memory Model:
the scheme of storing array elements.
Below is a diagram of basic array interfaces and classes.
Simple memory model
(the only model that supports all element types) |
||||
| Read-only access | Read/write access | Stack access (adding/removing the last element) | Full access | Access to internal Java array |
Interfaces:Array,BitArray,CharArray,ByteArray,ShortArray,IntArray,LongArray,FloatArray,DoubleArray,ObjectArray
|
Interfaces:UpdatableArray,UpdatableBitArray,UpdatableCharArray,UpdatableByteArray,UpdatableShortArray,UpdatableIntArray,UpdatableLongArray,UpdatableFloatArray,UpdatableDoubleArray,UpdatableObjectArray
|
Interfaces:Stack,BitStack,CharStack,ByteStack,ShortStack,IntStack,LongStack,FloatStack,DoubleStack,ObjectStack
|
Interfaces:MutableArray,MutableBitArray,MutableCharArray,MutableByteArray,MutableShortArray,MutableIntArray,MutableLongArray,MutableFloatArray,MutableDoubleArray,MutableObjectArray
|
Interface
DirectAccessible:
implemented by all arrays excepting bit (boolean) ones
and immutable instances
|
Buffer memory model
and Large memory model
(support all primitive element types) |
||||
| Read-only access | Read/write access | Stack access (adding/removing the last element) | Full access | Access to internal Java array |
Interfaces:Array,BitArray,CharArray,ByteArray,ShortArray,IntArray,LongArray,FloatArray,DoubleArray,(but not ObjectArray)
|
Interfaces:UpdatableArray,UpdatableBitArray,UpdatableCharArray,UpdatableByteArray,UpdatableShortArray,UpdatableIntArray,UpdatableLongArray,UpdatableFloatArray,UpdatableDoubleArray(but not UpdatableObjectArray)
|
Interfaces:Stack,BitStack,CharStack,ByteStack,ShortStack,IntStack,LongStack,FloatStack,DoubleStack,(but not ObjectStack)
|
Interfaces:MutableArray,MutableBitArray,MutableCharArray,MutableByteArray,MutableShortArray,MutableIntArray,MutableLongArray,MutableFloatArray,MutableDoubleArray,(but not MutableObjectArray)
|
Interface
DirectAccessible:
is never implemented
|
CombinedMemoryModel memory model
(supports only non-primitive element types) |
||||
| Read-only access | Read/write access | Stack access (adding/removing the last element) | Full access | Access to internal Java array |
Interfaces:Array,ObjectArray,ObjectInPlaceArray (optional)
|
Interfaces:UpdatableArray,UpdatableObjectArray,UpdatableObjectInPlaceArray (optional)
|
Interfaces:ObjectStack
|
Interfaces:MutableArray,MutableObjectArray,MutableObjectInPlaceArray (optional)
|
Interface
DirectAccessible:
is never implemented
|
There are special superinterfaces for some groups of primitive types, allowing to specify any array with elements from such groups. The hierarchy is the following:
Array subinterfaces:
PArray subinterfaces:
PFixedArray subinterfaces:
BitArrayCharArrayPIntegerArray subinterfaces:
PFloatingArray subinterfaces:
ObjectArrayAlso, all subinterfaces of PFixedArray and
PFloatingArray are grouped into the common interface
PNumberArray (any primitive types excepting boolean
and char, alike java.lang.Number class).
There are the same hierarchies for updatable and mutable arrays, but not for stacks.
The maximal possible length of AlgART array depends on the
memory model that has created this array.
An attempt to create an array with length exceeding the limit, specified by the memory model,
or an attempt to increase the length
or capacity
of an existing array over this limit, leads to
TooLargeArrayException (instead of the usual OutOfMemoryError).
The maximal array lengths for different memory models are listed below.
Simple memory modelThe maximal array length is defined by the language limitations for arrays. So, it cannot exceed 231-1 — the maximal possible length of Java arrays, excepting bit arrays, that can contain up to 237-1 because they are packed into long[]. However, real Java Machines usually limit the maximal length of arrays by 231-1 bytes (though the language theoretically allows to defined an array with 231-1 elements). It reduces the maximal possible length of AlgART arrays. |
||
| The type of elements | Theoretical limit for array length | Usual real limit for array length |
boolean (BitArray) char ( CharArray) byte ( ByteArray) short ( ShortArray) int ( IntArray) long ( LongArray) float ( FloatArray) double ( DoubleArray) Object ( ObjectArray)
|
237-1 231-1 231-1 231-1 231-1 231-1 231-1 231-1 231-1 |
234-1 230-1 231-1 230-1 229-1 228-1 229-1 228-1 depends on JVM implementation and the size of objects. |
| The real limits are less in 32-bit JVM,
that usually cannot utilize 2 GB of memory. |
Buffer memory modelThe maximal array length is defined by the Java API limitations for ByteBuffer class. This API use int type for the buffer length and allows creating direct NIO buffers only as views of ByteBuffer. So, the limit is 231-1 bytes. |
|
| The type of elements | The limit for array length |
boolean (BitArray) char ( CharArray) byte ( ByteArray) short ( ShortArray) int ( IntArray) long ( LongArray) float ( FloatArray) double ( DoubleArray)
|
234-1 230-1 231-1 230-1 229-1 228-1 229-1 228-1 |
| The real limits are less in 32-bit JVM,
that usually cannot utilize 2 GB of memory. |
Large memory modelThe maximal array length is limited by 263-1 bytes (the maximal supported file length in Java API and most OS), but also, of course, cannot exceed the common limit 263-1 elements (that is more strict limitation for bit arrays). |
|
| The type of elements | The limit for array length |
boolean (BitArray) char ( CharArray) byte ( ByteArray) short ( ShortArray) int ( IntArray) long ( LongArray) float ( FloatArray) double ( DoubleArray)
|
263-1 262-1 263-1 262-1 261-1 260-1 261-1 260-1 |
| In other words, the limits are so large that the real maximal array length
depends only on the available disk space. |
Combined memory modelThe maximal array length depends on the corresponding limit for a memory model, that is used by the combiner
which defines an algorithm of storing objects.
For example, if the storage is based on Large memory model,
the maximal array length usually depends only on the available disk space. |
There is an often and important problem to protect some application data against unallowed changes, to avoid hard bugs connected with unexpected damage of application objects. Below is a typical code illustraging this problem:
DataClass a = ...; // some important data someResults = someObject.process(a); // some method that need read-only access to the argument
Here a is some "important" data, that must stay immutable while the following call of process method. Maybe, for example, some parallel threads are reading this object now. And someObject.process is a method, which, theoretically, should not correct the passed data: it only analyzes it and creates some result. But it's very possible, that we are not sure, that this method really fulfils it. Maybe, its implementation is downloaded from Internet (and can be written by a hacker to damage our application). Or this method performs very complex tasks, and we cannot be sure that it doesn't contain bugs.
Java arrays offer only one way to protect data against changes and to solve this issue: cloning an array. An example:
int[] a = ...; // some important array int[] protected = (int[])a.clone(); someResults = someObject.process(protected);
Here the process method may corrupt the passed argument, but the original array will stay unchanged.
Standard Java collections, as well as buffers from java.nio packages, offer an additional method: making an immutable view. For example:
List a = ...; // some important list List protected = Collections.unmodifiableList(a); someResults = someObject.process(protected);
Now, if the process method will try to correct the passed argument, an exception will be thrown. This solution has an advantage: no additional memory is required for storing a clone.
AlgART array architecture supports 5 ways for solving this task, including 2 ways described above. We shall compare all them below.
The 1st solution is the simplest, fastest, but not safe enough. It is a syntactical solution. If the process method does not need to modify its argument, it should be declared with Array argument type, which doesn't contain any mutation methods at all:
public ResultType process(Array a);
A usage example:
Array a = ...; // maybe, there is MutableArray in this expression someResults = someObject.process(a);
Of course, it is not a problem to write a "malicious" process method which will correct its argument by operators alike the following: ((MutableArray)a).set(0, ...). However, if process method is written by you or by your colleagues, and you only need to protect against possible bugs, the syntactical protection will help you.
It is a very simple and absolutely safe solution:
Array a = ...; Array protected = a.updatableClone(); // or a.mutableClone()someResults = someObject.process(protected);
Unfortunately, such a solution requires additional memory and time, even if the process method, really, does not try do modify its argument.
It is a traditional, also simple and absolutely safe method, used by standard Java collections and NIO buffers:
Array a = ...;
Array protected = a.asImmutable();
someResults = someObject.process(protected);
The difference from the analogous technique, implemented in standard Java libraries,
is absence of "optional" operations. In a case of Java collections, process
method will have an ability to call a mutation method
for the passed array, but this method will throw an exception.
Unlike this, Array.asImmutable() method returns
an object that does not implement any interfaces and does not contain
any methods, which allow to change data anyhow.
The main defect of this solution is disabling any possible optimization, based on direct access
to stored data. For example, DirectAccessible interface may allow access to
the Java array, internally used for storing elements. If process method needs a lot
of accesses to elements in random order, then using DirectAccessible interface
in a separate algorithm branche can optimize the method in times, in a case when the AlgART array is really
based on Java arrays. Unfortunately, an immutable view has no right to provide such direct access
to internal storage, because it is a possible way to corrupt the array.
It is a compromise between absolute safety, provided by cloning and immutable views, and maximal efficiency, achieved while using syntactical protection only. An example of usage:
Array a = ...; Array protected = a.asTrustedImmutable(); try { someResults = someObject.process(protected); } finally { protected.checkUnallowedMutation(); }
Unlike usual immutable view, a trusted immutable view may implement some interfaces,
that allow to change the array content — only if it is really necessary for
optimization. (The only example of such interface in this package is DirectAccessible.)
So, the process method may corrupt the original array a.
However, any changes in the original array will be detected by the following call
"protected.checkUnallowedMutation()" with almost 100% probability,
and if the array was changed, UnallowedMutationError will be thrown.
To detect changes, checkUnallowedMutation usually calculates a hash code
and compares it with the hash code calculated in asTrustedImmutable method.
This technique is a suitable solution if you trust the authors of process method (for example, it is written by you or your colleagues), but this method is not trivial and you are not sure that all possible bugs in this method are already fixed. Unlike all other 4 protection methods, it is the only way to automatically detect such bugs: so, trusted immutable views may be very useful in a stage of testing application.
This solution have the following defects.
asTrustedImmutable() and
checkUnallowedMutation() methods.
(However, as well as immutable views, this method does not require any additional memory.)UnallowedMutationError.It is a more efficent alternative to cloning an array. This solution is also absolutely safe, but, sometimes, it requires additional memory and time. An example:
Array a = ...;
Array protected = a.asCopyOnNextWrite();
someResults = someObject.process(protected);
Now process method may freely change the passed argument (if it implements necessary
interfaces). However, the first (not further!) attempt to modify the passed protected array,
or any other access that can lead to its modification (like DirectAccessible.javaArray()
method), will lead to reallocation of the underlying storage, used for array elements,
before performing the operation. It means that modification will not affect
the original a array, but only protected array.
This solution is the best choince, if you need a strict guarantee that the original array
will not be modified (that is not provided by trusted immutable views), and you don't need
a guarantee that no additional memory will be occupied. If the process method
will not try to modify the array or use optimization interfaces alike DirectAccessible,
then this solution will provide the maximal efficiency.
If the method will try to get direct access for optimization via DirectAccessible
interface, then the internal data will be cloned at this moment, that can require additional memory and time,
but all further accesses to elements will work with maximal efficiency.
This solution have the following defects.
DirectAccessible
interface), and the passed array really allows this optimizaion (for example, is based on Java arrays).
Good processing methods may use Array.isCopyOnNextWrite() method
to choose the best behaviour.asCopyOnNextWrite().asTrustedImmutable()" Such protection is also absolutely safe,
but also allows to catch unallowed attempts of correction by
checkUnallowedMutation() method.Immutable AlgART arrays are absolutely thread-safe
and can be used simultaneously in several threads.
Moreover, even if an AlgART array is mutable (for example, implements MutableArray),
but all threads, accessing it, only read data from it and do not attempt to modify the array by any way,
then this array is also thread-safe and no synchronization is required.
(The same rules are correct for usual Java arrays.)
If there are 2 or more threads accessing an AlgART array, and at least one from them modifies it
(for example, changes elements or the length), then you should synchronize access to the array.
Without external synchronization, the resulting data in the array will be unspecified.
However, if you do not use any methods from MutableArray /
Stack interfaces and their inheritor,
but only read and write elements via methods provided UpdatableArray interface
(and its versions for concrete element types),
then the behaviour while simultaneous multithreading access will be the same as for usual Java arrays.
In particular, access to one element will never affect another elements.
So, you can correctly simultaneously work with several non-overlapping sets of elements of the same array
from several threads without synchronization, if different threads work with different sets.
(Please compare: the standard java.util.BitSet class does not provide such guarantees.)
The methods of classes implementing AlgART arrays, usually, may throw exceptions declared in the Javadoc comments to methods. In addition, there are following exception, that may be thrown by methods and are not always specified in comments.
Large memory model,
and there is some problem with access to this file, for example, not enough disk space.
Large memory model.
In this case, the built-in shutdown hook is started to remove all temporarily allocated disk files,
and since it is started, almost any access to an AlgART array, based on a temporary file,
lead to IOError with IllegalStateException as a cause.
Large memory model,
if the current thread is interrupted by Thread.interrupt() method.
Also this error is thrown if the Thread.interrupt() method is called for a thread,
that is currently performing multithread copying by copy method.
Usually, such behaviour is not suitable. So, you should not try to interrupt the
threads, processing AlgART arrays, via Thread.interrupt() technique!
Please use an alternative technique: some volatile flag, required interruption,
or net.algart.contexts.InterruptionContext interface.
For interruption of Arrays.copy method,
you may also use the custom implementation of ArrayContext.
Arrays.copy method,
if the context, passed to this method,
throws this exception in its checkInterruption() method. It is the recommended way of interrupting
Arrays.copy method.Behaviour of AlgART arrays depends on some system properties, that allow to customize many important aspects. Below is the list of these properties.
memory model,
that may be used in your classes which need AlgART arrays.
The simple memory model is used by default.
See Arrays.SystemSettings.globalMemoryModel() for more details.Arrays.SystemSettings.maxTempJavaMemory() for more details.Arrays.SystemSettings.maxMultithreadingArraySize() for more details.DefaultDataFileModel class.
May contain any nonnegative long value.
Default value is 268435456 (256 MB).
See DefaultDataFileModel.maxMappedMemory() for more details.DefaultThreadPoolFactory.recommendedNumberOfTasks()
for more details.DefaultThreadPoolFactory.globalThreadPool()
for more details.Arrays.SystemSettings.profilingMode() for more details.data file model,
used by the Large memory model.
DefaultDataFileModel is used by default.
See LargeMemoryModel.getInstance() for more details.
default data file model.
Default value is 3.
See DefaultDataFileModel.recommendedNumberOfBanks() for more details.default data file model
for unresizable arrays (on 64-bit Java machines).
Default value is 4194304 (4 MB).
See DefaultDataFileModel.recommendedBankSize(boolean) with
true argument for more details.default data file model
for resizable arrays (on 64-bit Java machines).
Default value is 262144 (256 KB).
See DefaultDataFileModel.recommendedBankSize(boolean) with
false argument for more details.default data file model
(on 64-bit Java machines).
Default value is 33554432 (32 MB).
See DefaultDataFileModel.recommendedSingleMappingLimit() for more details.default data file model
for unresizable arrays (on 32-bit Java machines).
Default value is 1048576 (1 MB).
See DefaultDataFileModel.recommendedBankSize(boolean) with
true argument for more details.default data file model
for resizable arrays (on 32-bit Java machines).
Default value is 131072 (128 KB).
See DefaultDataFileModel.recommendedBankSize(boolean) with
false argument for more details.default data file model
(on 32-bit Java machines).
Default value is 2097152 (2 MB).
See DefaultDataFileModel.recommendedSingleMappingLimit() for more details.default data file model
should increase the file size via standard I/O API, or it is increased automatically
as a result of new mappings.
Default value is false.
See DefaultDataFileModel.autoResizingOnMapping() for more details.default data file model
will use lazy-writing mode by default.
Default value is true in Java 1.7 or higher Java version and false in Java 1.5 and Java 1.6.
See DefaultDataFileModel.DefaultDataFileModel(java.io.File, long)
consturctor for more details.