コード例 #1
0
        void ValidateSubRowRange(MatrixStorage <T> target, int rowIndex,
                                 int sourceColumnIndex, int targetColumnIndex, int columnCount)
        {
            if (columnCount < 1)
            {
                throw new ArgumentOutOfRangeException(nameof(columnCount), "Value must be positive.");
            }

            // Verify Source

            if ((uint)sourceColumnIndex >= (uint)Length)
            {
                throw new ArgumentOutOfRangeException(nameof(sourceColumnIndex));
            }

            if (sourceColumnIndex + columnCount > Length)
            {
                throw new ArgumentOutOfRangeException(nameof(columnCount));
            }

            // Verify Target

            if ((uint)rowIndex >= (uint)target.RowCount)
            {
                throw new ArgumentOutOfRangeException(nameof(rowIndex));
            }

            if ((uint)targetColumnIndex >= (uint)target.ColumnCount)
            {
                throw new ArgumentOutOfRangeException(nameof(targetColumnIndex));
            }

            if (targetColumnIndex + columnCount > target.ColumnCount)
            {
                throw new ArgumentOutOfRangeException(nameof(columnCount));
            }
        }
コード例 #2
0
        // TRANSPOSE

        internal override void TransposeToUnchecked(MatrixStorage <T> target, ExistingData existingData)
        {
            if (target is DenseColumnMajorMatrixStorage <T> denseTarget)
            {
                TransposeToUnchecked(denseTarget);
                return;
            }

            if (target is SparseCompressedRowMatrixStorage <T> sparseTarget)
            {
                TransposeToUnchecked(sparseTarget);
                return;
            }

            // FALL BACK

            for (int j = 0, offset = 0; j < ColumnCount; j++, offset += RowCount)
            {
                for (int i = 0; i < RowCount; i++)
                {
                    target.At(j, i, Data[i + offset]);
                }
            }
        }
コード例 #3
0
        internal override void CopySubMatrixToUnchecked(MatrixStorage <T> target,
                                                        int sourceRowIndex, int targetRowIndex, int rowCount,
                                                        int sourceColumnIndex, int targetColumnIndex, int columnCount,
                                                        ExistingData existingData)
        {
            if (target is DenseColumnMajorMatrixStorage <T> denseTarget)
            {
                CopySubMatrixToUnchecked(denseTarget, sourceRowIndex, targetRowIndex, rowCount, sourceColumnIndex, targetColumnIndex, columnCount);
                return;
            }

            // TODO: Proper Sparse Implementation

            // FALL BACK

            for (int j = sourceColumnIndex, jj = targetColumnIndex; j < sourceColumnIndex + columnCount; j++, jj++)
            {
                int index = sourceRowIndex + j * RowCount;
                for (int ii = targetRowIndex; ii < targetRowIndex + rowCount; ii++)
                {
                    target.At(ii, jj, Data[index++]);
                }
            }
        }
コード例 #4
0
        internal override Tuple <int, int, T, TOther> Find2Unchecked <TOther>(MatrixStorage <TOther> other, Func <T, TOther, bool> predicate, Zeros zeros)
        {
            if (other is DenseColumnMajorMatrixStorage <TOther> denseOther)
            {
                TOther[] otherData = denseOther.Data;
                for (int i = 0; i < Data.Length; i++)
                {
                    if (predicate(Data[i], otherData[i]))
                    {
                        int row, column;
                        RowColumnAtIndex(i, out row, out column);
                        return(new Tuple <int, int, T, TOther>(row, column, Data[i], otherData[i]));
                    }
                }
                return(null);
            }

            if (other is DiagonalMatrixStorage <TOther> diagonalOther)
            {
                TOther[] otherData = diagonalOther.Data;
                TOther   otherZero = BuilderInstance <TOther> .Matrix.Zero;
                int      k         = 0;
                for (int j = 0; j < ColumnCount; j++)
                {
                    for (int i = 0; i < RowCount; i++)
                    {
                        if (predicate(Data[k], i == j ? otherData[i] : otherZero))
                        {
                            return(new Tuple <int, int, T, TOther>(i, j, Data[k], i == j ? otherData[i] : otherZero));
                        }
                        k++;
                    }
                }
                return(null);
            }

            if (other is SparseCompressedRowMatrixStorage <TOther> sparseOther)
            {
                int[]    otherRowPointers   = sparseOther.RowPointers;
                int[]    otherColumnIndices = sparseOther.ColumnIndices;
                TOther[] otherValues        = sparseOther.Values;
                TOther   otherZero          = BuilderInstance <TOther> .Matrix.Zero;
                int      k = 0;
                for (int row = 0; row < RowCount; row++)
                {
                    for (int col = 0; col < ColumnCount; col++)
                    {
                        if (k < otherRowPointers[row + 1] && otherColumnIndices[k] == col)
                        {
                            if (predicate(Data[col * RowCount + row], otherValues[k]))
                            {
                                return(new Tuple <int, int, T, TOther>(row, col, Data[col * RowCount + row], otherValues[k]));
                            }
                            k++;
                        }
                        else
                        {
                            if (predicate(Data[col * RowCount + row], otherZero))
                            {
                                return(new Tuple <int, int, T, TOther>(row, col, Data[col * RowCount + row], otherValues[k]));
                            }
                        }
                    }
                }
                return(null);
            }

            // FALL BACK

            return(base.Find2Unchecked(other, predicate, zeros));
        }
コード例 #5
0
        internal override void MapSubMatrixIndexedToUnchecked <TU>(MatrixStorage <TU> target, Func <int, int, T, TU> f,
                                                                   int sourceRowIndex, int targetRowIndex, int rowCount,
                                                                   int sourceColumnIndex, int targetColumnIndex, int columnCount,
                                                                   Zeros zeros, ExistingData existingData)
        {
            if (target is DiagonalMatrixStorage <TU> diagonalTarget)
            {
                MapSubMatrixIndexedToUnchecked(diagonalTarget, f, sourceRowIndex, targetRowIndex, rowCount, sourceColumnIndex, targetColumnIndex, columnCount, zeros);
                return;
            }

            if (target is DenseColumnMajorMatrixStorage <TU> denseTarget)
            {
                MapSubMatrixIndexedToUnchecked(denseTarget, f, sourceRowIndex, targetRowIndex, rowCount, sourceColumnIndex, targetColumnIndex, columnCount, zeros, existingData);
                return;
            }

            // TODO: Proper Sparse Implementation

            // FALL BACK

            if (existingData == ExistingData.Clear)
            {
                target.ClearUnchecked(targetRowIndex, rowCount, targetColumnIndex, columnCount);
            }

            if (sourceRowIndex == sourceColumnIndex)
            {
                int targetRow    = targetRowIndex;
                int targetColumn = targetColumnIndex;
                for (var i = 0; i < Math.Min(columnCount, rowCount); i++)
                {
                    target.At(targetRow, targetColumn, f(targetRow, targetColumn, Data[sourceRowIndex + i]));
                    targetRow++;
                    targetColumn++;
                }
            }
            else if (sourceRowIndex > sourceColumnIndex && sourceColumnIndex + columnCount > sourceRowIndex)
            {
                // column by column, but skip resulting zero columns at the beginning
                int columnInit   = sourceRowIndex - sourceColumnIndex;
                int targetRow    = targetRowIndex;
                int targetColumn = targetColumnIndex + columnInit;
                for (var i = 0; i < Math.Min(columnCount - columnInit, rowCount); i++)
                {
                    target.At(targetRow, targetColumn, f(targetRow, targetColumn, Data[sourceRowIndex + i]));
                    targetRow++;
                    targetColumn++;
                }
            }
            else if (sourceRowIndex < sourceColumnIndex && sourceRowIndex + rowCount > sourceColumnIndex)
            {
                // row by row, but skip resulting zero rows at the beginning
                int rowInit      = sourceColumnIndex - sourceRowIndex;
                int targetRow    = targetRowIndex + rowInit;
                int targetColumn = targetColumnIndex;
                for (var i = 0; i < Math.Min(columnCount, rowCount - rowInit); i++)
                {
                    target.At(targetRow, targetColumn, f(targetRow, targetColumn, Data[sourceColumnIndex + i]));
                    targetRow++;
                    targetColumn++;
                }
            }
        }
コード例 #6
0
        internal override Tuple <int, int, T, TOther> Find2Unchecked <TOther>(MatrixStorage <TOther> other, Func <T, TOther, bool> predicate, Zeros zeros)
        {
            if (other is DenseColumnMajorMatrixStorage <TOther> denseOther)
            {
                TOther[] otherData = denseOther.Data;
                int      k         = 0;
                for (int j = 0; j < ColumnCount; j++)
                {
                    for (int i = 0; i < RowCount; i++)
                    {
                        if (predicate(i == j ? Data[i] : Zero, otherData[k]))
                        {
                            return(new Tuple <int, int, T, TOther>(i, j, i == j ? Data[i] : Zero, otherData[k]));
                        }
                        k++;
                    }
                }
                return(null);
            }

            if (other is DiagonalMatrixStorage <TOther> diagonalOther)
            {
                TOther[] otherData = diagonalOther.Data;
                for (int i = 0; i < Data.Length; i++)
                {
                    if (predicate(Data[i], otherData[i]))
                    {
                        return(new Tuple <int, int, T, TOther>(i, i, Data[i], otherData[i]));
                    }
                }
                if (zeros == Zeros.Include && (RowCount > 1 || ColumnCount > 1))
                {
                    TOther otherZero = BuilderInstance <TOther> .Matrix.Zero;
                    if (predicate(Zero, otherZero))
                    {
                        return(new Tuple <int, int, T, TOther>(RowCount > 1 ? 1 : 0, RowCount > 1 ? 0 : 1, Zero, otherZero));
                    }
                }
                return(null);
            }

            if (other is SparseCompressedRowMatrixStorage <TOther> sparseOther)
            {
                int[]    otherRowPointers   = sparseOther.RowPointers;
                int[]    otherColumnIndices = sparseOther.ColumnIndices;
                TOther[] otherValues        = sparseOther.Values;
                TOther   otherZero          = BuilderInstance <TOther> .Matrix.Zero;
                for (int row = 0; row < RowCount; row++)
                {
                    bool diagonal   = false;
                    var  startIndex = otherRowPointers[row];
                    var  endIndex   = otherRowPointers[row + 1];
                    for (var j = startIndex; j < endIndex; j++)
                    {
                        if (otherColumnIndices[j] == row)
                        {
                            diagonal = true;
                            if (predicate(Data[row], otherValues[j]))
                            {
                                return(new Tuple <int, int, T, TOther>(row, row, Data[row], otherValues[j]));
                            }
                        }
                        else
                        {
                            if (predicate(Zero, otherValues[j]))
                            {
                                return(new Tuple <int, int, T, TOther>(row, otherColumnIndices[j], Zero, otherValues[j]));
                            }
                        }
                    }
                    if (!diagonal && row < ColumnCount)
                    {
                        if (predicate(Data[row], otherZero))
                        {
                            return(new Tuple <int, int, T, TOther>(row, row, Data[row], otherZero));
                        }
                    }
                }
                if (zeros == Zeros.Include && sparseOther.ValueCount < (RowCount * ColumnCount))
                {
                    if (predicate(Zero, otherZero))
                    {
                        int k = 0;
                        for (int row = 0; row < RowCount; row++)
                        {
                            for (int col = 0; col < ColumnCount; col++)
                            {
                                if (k < otherRowPointers[row + 1] && otherColumnIndices[k] == col)
                                {
                                    k++;
                                }
                                else if (row != col)
                                {
                                    return(new Tuple <int, int, T, TOther>(row, col, Zero, otherZero));
                                }
                            }
                        }
                    }
                }
                return(null);
            }

            // FALL BACK

            return(base.Find2Unchecked(other, predicate, zeros));
        }
コード例 #7
0
        // TRANSPOSE

        internal override void TransposeToUnchecked(MatrixStorage <T> target, ExistingData existingData)
        {
            CopyToUnchecked(target, existingData);
        }
コード例 #8
0
        internal override TState Fold2Unchecked <TOther, TState>(MatrixStorage <TOther> other, Func <TState, T, TOther, TState> f, TState state, Zeros zeros)
        {
            if (other is DenseColumnMajorMatrixStorage <TOther> denseOther)
            {
                TOther[] otherData = denseOther.Data;
                int      k         = 0;
                for (int j = 0; j < ColumnCount; j++)
                {
                    for (int i = 0; i < RowCount; i++)
                    {
                        state = f(state, i == j ? Data[i] : Zero, otherData[k]);
                        k++;
                    }
                }
                return(state);
            }

            if (other is DiagonalMatrixStorage <TOther> diagonalOther)
            {
                TOther[] otherData = diagonalOther.Data;
                for (int i = 0; i < Data.Length; i++)
                {
                    state = f(state, Data[i], otherData[i]);
                }

                // Do we really need to do this?
                if (zeros == Zeros.Include)
                {
                    TOther otherZero = BuilderInstance <TOther> .Matrix.Zero;
                    int    count     = RowCount * ColumnCount - Data.Length;
                    for (int i = 0; i < count; i++)
                    {
                        state = f(state, Zero, otherZero);
                    }
                }

                return(state);
            }

            if (other is SparseCompressedRowMatrixStorage <TOther> sparseOther)
            {
                int[]    otherRowPointers   = sparseOther.RowPointers;
                int[]    otherColumnIndices = sparseOther.ColumnIndices;
                TOther[] otherValues        = sparseOther.Values;
                TOther   otherZero          = BuilderInstance <TOther> .Matrix.Zero;

                if (zeros == Zeros.Include)
                {
                    int k = 0;
                    for (int row = 0; row < RowCount; row++)
                    {
                        for (int col = 0; col < ColumnCount; col++)
                        {
                            if (k < otherRowPointers[row + 1] && otherColumnIndices[k] == col)
                            {
                                state = f(state, row == col ? Data[row] : Zero, otherValues[k++]);
                            }
                            else
                            {
                                state = f(state, row == col ? Data[row] : Zero, otherZero);
                            }
                        }
                    }
                    return(state);
                }

                for (int row = 0; row < RowCount; row++)
                {
                    bool diagonal = false;

                    var startIndex = otherRowPointers[row];
                    var endIndex   = otherRowPointers[row + 1];
                    for (var j = startIndex; j < endIndex; j++)
                    {
                        if (otherColumnIndices[j] == row)
                        {
                            diagonal = true;
                            state    = f(state, Data[row], otherValues[j]);
                        }
                        else
                        {
                            state = f(state, Zero, otherValues[j]);
                        }
                    }

                    if (!diagonal && row < ColumnCount)
                    {
                        state = f(state, Data[row], otherZero);
                    }
                }

                return(state);
            }

            // FALL BACK

            return(base.Fold2Unchecked(other, f, state, zeros));
        }
コード例 #9
0
        void ValidateSubMatrixRange <TU>(MatrixStorage <TU> target,
                                         int sourceRowIndex, int targetRowIndex, int rowCount,
                                         int sourceColumnIndex, int targetColumnIndex, int columnCount)
            where TU : struct, IEquatable <TU>, IFormattable
        {
            if (rowCount < 1)
            {
                throw new ArgumentOutOfRangeException(nameof(rowCount), "Value must be positive.");
            }

            if (columnCount < 1)
            {
                throw new ArgumentOutOfRangeException(nameof(columnCount), "Value must be positive.");
            }

            // Verify Source

            if ((uint)sourceRowIndex >= (uint)RowCount)
            {
                throw new ArgumentOutOfRangeException(nameof(sourceRowIndex));
            }

            if ((uint)sourceColumnIndex >= (uint)ColumnCount)
            {
                throw new ArgumentOutOfRangeException(nameof(sourceColumnIndex));
            }

            var sourceRowMax    = sourceRowIndex + rowCount;
            var sourceColumnMax = sourceColumnIndex + columnCount;

            if (sourceRowMax > RowCount)
            {
                throw new ArgumentOutOfRangeException(nameof(rowCount));
            }

            if (sourceColumnMax > ColumnCount)
            {
                throw new ArgumentOutOfRangeException(nameof(columnCount));
            }

            // Verify Target

            if ((uint)targetRowIndex >= (uint)target.RowCount)
            {
                throw new ArgumentOutOfRangeException(nameof(targetRowIndex));
            }

            if ((uint)targetColumnIndex >= (uint)target.ColumnCount)
            {
                throw new ArgumentOutOfRangeException(nameof(targetColumnIndex));
            }

            var targetRowMax    = targetRowIndex + rowCount;
            var targetColumnMax = targetColumnIndex + columnCount;

            if (targetRowMax > target.RowCount)
            {
                throw new ArgumentOutOfRangeException(nameof(rowCount));
            }

            if (targetColumnMax > target.ColumnCount)
            {
                throw new ArgumentOutOfRangeException(nameof(columnCount));
            }
        }