SquareDenseMatrix.java
package org.djunits.vecmat.def;
import java.util.Arrays;
import org.djunits.quantity.SIQuantity;
import org.djunits.quantity.def.Quantity;
import org.djunits.unit.UnitInterface;
import org.djunits.unit.si.SIUnit;
import org.djutils.exceptions.Throw;
/**
* SquareDenseMatrix implements the core functions for a matrix with n x n real-valued entries. The data is stored in a dense
* double[] field. The matrix is immutable, except for the display unit, which can be changed.
* <p>
* Copyright (c) 2025-2026 Delft University of Technology, Jaffalaan 5, 2628 BX Delft, the Netherlands. All rights reserved. See
* for project information <a href="https://djunits.org" target="_blank">https://djunits.org</a>. The DJUNITS project is
* distributed under a <a href="https://djunits.org/docs/license.html" target="_blank">three-clause BSD-style license</a>.
* @author Alexander Verbraeck
* @param <Q> the quantity type
* @param <U> the unit type
* @param <M> the 'SELF' square dense matrix type
* @param <SI> the square dense matrix type with generics <SIQuantity, SIUnit<
* @param <H> the generic square dense matrix type with generics <?, ?< for Hadamard operations
*/
public abstract class SquareDenseMatrix<Q extends Quantity<Q, U>, U extends UnitInterface<U, Q>,
M extends SquareDenseMatrix<Q, U, M, SI, H>, SI extends SquareDenseMatrix<SIQuantity, SIUnit, SI, ?, ?>,
H extends SquareDenseMatrix<?, ?, ?, ?, ?>> extends SquareMatrix<Q, U, M, SI, H>
{
/** */
private static final long serialVersionUID = 600L;
/** The n x n values in si-units. */
private final double[] dataSi;
/** the order (n in n x n) of the matrix. */
private final int order;
/**
* Create a new SquareDenseMatrix with a unit.
* @param dataInUnit the matrix values {a11, a12, ..., a21, a22, ...} expressed in the display unit
* @param displayUnit the display unit to use
* @param order the order of the square matrix (number of rows/columns)
*/
protected SquareDenseMatrix(final double[] dataInUnit, final U displayUnit, final int order)
{
super(displayUnit);
Throw.when(dataInUnit.length != order * order, IllegalArgumentException.class,
"SquareDenseMatrix initialized with %d values instead of %d", dataInUnit.length, order * order);
this.dataSi = new double[dataInUnit.length];
for (int i = 0; i < this.dataSi.length; i++)
{
this.dataSi[i] = displayUnit.toBaseValue(dataInUnit[i]);
}
this.order = order;
}
@Override
public double[] si()
{
return this.dataSi;
}
@Override
public double si(final int row, final int col)
{
checkRow(row);
checkCol(col);
return this.dataSi[this.order * row + col];
}
@Override
public int rows()
{
return this.order;
}
@Override
public int cols()
{
return this.order;
}
@Override
public double[] getRowSi(final int row)
{
checkRow(row);
double[] vSi = new double[this.order];
for (int col = 0; col < this.order; col++)
{
vSi[col] = this.dataSi[this.order * row + col];
}
return vSi;
}
@Override
public double[] getColumnSi(final int col)
{
checkCol(col);
double[] vSi = new double[this.order];
for (int row = 0; row < this.order; row++)
{
vSi[row] = this.dataSi[this.order * row + col];
}
return vSi;
}
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + Arrays.hashCode(this.dataSi);
return result;
}
@SuppressWarnings("checkstyle:needbraces")
@Override
public boolean equals(final Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
SquareDenseMatrix<?, ?, ?, ?, ?> other = (SquareDenseMatrix<?, ?, ?, ?, ?>) obj;
return Arrays.equals(this.dataSi, other.dataSi);
}
}