private static void TestReorderingCamdSuiteSparse()
        {
            Skip.IfNot(TestSettings.TestSuiteSparse, TestSettings.MessageWhenSkippingSuiteSparse);

            int n           = SparsePosDef10by10.Order;
            var pattern     = SparsityPatternSymmetric.CreateFromDense(Matrix.CreateFromArray(SparsePosDef10by10.Matrix));
            var orderingAlg = new OrderingCamdSuiteSparse();

            (int[] permutation, ReorderingStatistics stats) =
                orderingAlg.FindPermutation(pattern, SparsePosDef10by10.ConstraintsCAMD);

            var originalDiagonal = new double[n];
            var permutedDiagonal = new double[n];

            for (int i = 0; i < n; ++i)
            {
                originalDiagonal[i] = SparsePosDef10by10.Matrix[i, i];
            }
            for (int i = 0; i < n; ++i)
            {
                permutedDiagonal[i] = originalDiagonal[permutation[i]];
            }

            var writer = new Array1DWriter();

            Console.Write("Permutation (new-to-old): ");
            writer.WriteToConsole(permutation);
            Console.Write("Original diagonal: ");
            writer.WriteToConsole(originalDiagonal);
            Console.Write("Permuted diagonal: ");
            writer.WriteToConsole(permutedDiagonal);

            comparer.AssertEqual(SparsePosDef10by10.PermutationCAMD, permutation);
        }
        public void ReorderCornerDofs(FetiDPDofSeparator dofSeparator)
        {
            if (reordering == null)
            {
                return;                     // Use the natural ordering and do not modify any stored dof data
            }
            var pattern = SparsityPatternSymmetric.CreateEmpty(dofSeparator.NumGlobalCornerDofs);

            for (int s = 0; s < subdomains.Count; ++s)
            {
                // Treat each subdomain as a superelement with only its corner nodes.
                var localCornerDofOrdering = dofSeparator.SubdomainCornerDofOrderings[s];
                int numLocalCornerDofs     = localCornerDofOrdering.EntryCount;
                var subdomainToGlobalDofs  = new int[numLocalCornerDofs];
                foreach ((INode node, IDofType dofType, int localIdx) in localCornerDofOrdering)
                {
                    int globalIdx = dofSeparator.GlobalCornerDofOrdering[node, dofType];
                    subdomainToGlobalDofs[localIdx] = globalIdx;
                }
                pattern.ConnectIndices(subdomainToGlobalDofs, false);
            }
            (int[] permutation, bool oldToNew) = reordering.FindPermutation(pattern);
            dofSeparator.GlobalCornerDofOrdering.Reorder(permutation, oldToNew);
            dofSeparator.GlobalCornerToFreeDofMap =
                ReorderingUtilities.ReorderKeysOfDofIndicesMap(dofSeparator.GlobalCornerToFreeDofMap, permutation, oldToNew);
        }
        private static void TestReorderingAmdCSparseNet()
        {
            var pattern     = SparsityPatternSymmetric.CreateFromDense(Matrix.CreateFromArray(SparsePosDef10by10.Matrix));
            var orderingAlg = new OrderingAmdCSparseNet();

            (int[] permutation, bool oldToNew) = orderingAlg.FindPermutation(pattern);
            comparer.AssertEqual(SparsePosDef10by10.MatlabPermutationAMD, permutation);
        }
        private static void TestReorderingAmdSuiteSparse()
        {
            Skip.IfNot(TestSettings.TestSuiteSparse, TestSettings.MessageWhenSkippingSuiteSparse);

            var pattern     = SparsityPatternSymmetric.CreateFromDense(Matrix.CreateFromArray(SparsePosDef10by10.Matrix));
            var orderingAlg = new OrderingAmdSuiteSparse();

            (int[] permutation, bool oldToNew) = orderingAlg.FindPermutation(pattern);
            comparer.AssertEqual(SparsePosDef10by10.MatlabPermutationAMD, permutation);
        }
Ejemplo n.º 5
0
        //TODO: Move this method to SparsityPatternSymmetric, so that I can optimize access to its private data
        internal static SparsityPatternSymmetric GetSubmatrixSymmetricPattern(double[] skyValues, int[] skyDiagOffsets,
                                                                              int[] rowsColsToKeep)
        {
            //TODO: perhaps this can be combined with the CSC and full version to get all 2 submatrices needed for
            //      Schur complements more efficiently.

            int subOrder = rowsColsToKeep.Length;

            if (subOrder == 0)
            {
                throw new NonMatchingDimensionsException("The original matrix had 0 rows and columns.");
            }
            var submatrix = SparsityPatternSymmetric.CreateEmpty(subOrder);

            for (int subCol = 0; subCol < subOrder; ++subCol)
            {
                int col        = rowsColsToKeep[subCol];
                int diagOffset = skyDiagOffsets[col];
                int colHeight  = skyDiagOffsets[col + 1] - diagOffset - 1; // excluding diagonal
                for (int subRow = 0; subRow <= subCol; ++subRow)
                {
                    int row = rowsColsToKeep[subRow];
                    if (row <= col)
                    {
                        int entryHeight = col - row;  // excluding diagonal
                        if (entryHeight <= colHeight) // inside stored non zero pattern
                        {
                            double val = skyValues[diagOffset + entryHeight];
                            if (val != 0.0)
                            {
                                submatrix.AddEntryUpper(subRow, subCol);             // Skyline format stores many unnecessary zeros.
                            }
                        }
                    }
                    else // Transpose row <-> col. The cached column height and offset must be recalculated.
                    {
                        int transposedDiagOffset = skyDiagOffsets[row];
                        int transposedColHeight  = skyDiagOffsets[row + 1] - transposedDiagOffset - 1; // excluding diagonal
                        int entryHeight          = row - col;                                          // excluding diagonal
                        if (entryHeight <= transposedColHeight)                                        // inside stored non zero pattern
                        {
                            double val = skyValues[transposedDiagOffset + entryHeight];
                            if (val != 0.0)
                            {
                                submatrix.AddEntryUpper(subRow, subCol);             // Skyline format stores many unnecessary zeros.
                            }
                        }
                    }
                }
            }
            return(submatrix);
        }
Ejemplo n.º 6
0
        public void Reorder(IReorderingAlgorithm reorderingAlgorithm, ISubdomain subdomain)
        {
            var pattern = SparsityPatternSymmetric.CreateEmpty(NumFreeDofs);

            foreach (var element in subdomain.Elements)
            {
                (int[] elementDofIndices, int[] subdomainDofIndices) = MapFreeDofsElementToSubdomain(element);

                //TODO: ISubdomainFreeDofOrdering could perhaps return whether the subdomainDofIndices are sorted or not.
                pattern.ConnectIndices(subdomainDofIndices, false);
            }
            (int[] permutation, bool oldToNew) = reorderingAlgorithm.FindPermutation(pattern);
            FreeDofs.Reorder(permutation, oldToNew);
        }
        private static void TestSparsePosDef()
        {
            int n       = SparsePosDef10by10.Order;
            var pattern = SparsityPatternSymmetric.CreateEmpty(n);

            for (int i = 0; i < n; ++i)
            {
                for (int j = 0; j < n; ++j)
                {
                    if (SparsePosDef10by10.Matrix[i, j] != 0)
                    {
                        pattern.AddEntry(i, j);
                    }
                }
            }
            TestWriteOperation(pattern, SparsePosDef10by10.PatternPath);
        }
        private static void TestConnectIndices()
        {
            int n       = GlobalMatrixAssembly.GlobalOrder;
            var dense   = Matrix.CreateFromArray(GlobalMatrixAssembly.GlobalMatrix);
            var pattern = SparsityPatternSymmetric.CreateEmpty(n);

            pattern.ConnectIndices(GlobalMatrixAssembly.GlobalIndices1, true);
            pattern.ConnectIndices(GlobalMatrixAssembly.GlobalIndices2, true);
            pattern.ConnectIndices(GlobalMatrixAssembly.GlobalIndices3, true);

            for (int i = 0; i < n; ++i)
            {
                for (int j = 0; j < n; ++j)
                {
                    bool denseHasZero   = dense[i, j] == 0.0;
                    bool patternHasZero = !pattern.IsNonZero(i, j);
                    Assert.True(patternHasZero == denseHasZero);
                }
            }
        }