# Source code for openmdao.matrices.dense_matrix

"""Define the DenseMatrix class."""
import numpy as np

from openmdao.matrices.coo_matrix import COOMatrix

# NOTE: DenseMatrix is inherited from COOMatrix so that we can easily handle use cases
#       where partials overlap the same matrix entries, as in the case of repeated
#       src_indices entries.  This does require additional memory above storing just
#       the dense matrix, but it's worth it because the code is simpler and more robust.

[docs]class DenseMatrix(COOMatrix):
"""
Dense global matrix.
"""

def _build(self, num_rows, num_cols, system=None):
"""
Allocate the matrix.

Parameters
----------
num_rows : int
number of rows in the matrix.
num_cols : int
number of cols in the matrix.
system : <System>
owning system.
"""
super()._build(num_rows, num_cols)
self._coo = self._matrix

"""
Perform a matrix vector product.

Parameters
----------
in_vec : ndarray[:]
incoming vector to multiply.
mode : str
'fwd' or 'rev'.
mask : ndarray of type bool, or None
Array used to mask out part of the input vector.

Returns
-------
ndarray[:]
vector resulting from the product.
"""
# when we have a derivative based solver at a level below the
# group that owns the AssembledJacobian, we need to use only
# the part of the matrix that is relevant to the lower level
# system.
mat = self._matrix

if mode == 'fwd':
return mat.dot(in_vec)
else:
# Use the special dot product function from masking module so that we
else:  # rev
return mat.T.dot(in_vec)
else:
# Mask need to be applied to ext_mtx so that we can ignore multiplication
# by certain columns.
mat_T = mat.T

"""
Create masking array for this matrix.

Note: this only applies when this Matrix is an 'ext_mtx' inside of a
Jacobian object.

Parameters
----------
d_inputs : Vector
The inputs linear vector.

Returns
-------
ndarray or None
"""
if d_inputs._in_matvec_context():
sub = d_inputs._names
if key[1] in sub:

def _pre_update(self):
"""
Do anything that needs to be done at the end of AssembledJacobian._update.
"""
self._matrix = self._coo

def _post_update(self):
"""
Do anything that needs to be done at the end of AssembledJacobian._update.
"""
# this will add any repeated entries together
self._matrix = self._coo.toarray()