示例#1
0
        /// <summary>
        /// creates the new incidence matrix based on the SCCs. SCCs are clustered in the new DSM in a single row.
        /// </summary>
        /// <param name="IM"></param>
        /// <param name="clusters"></param>
        /// <returns></returns>
        private static IncidenceMatrix CreateUpMatrix(IncidenceMatrix IM, List <Cluster> clusters)
        {
            IncidenceMatrix imMatrixU = IncidenceMatrix.Build.Dense(clusters.Count, IM.ColumnCount);

            for (int r = 0; r < clusters.Count; r++)
            {
                Cluster cluster = clusters[r];
                if (cluster.Count == 1)
                {
                    imMatrixU.SetRow(r, IM.Row(cluster[0]));
                }
                else
                {
                    IncidenceMatrix imMatrixT = IncidenceMatrix.Build.Dense(cluster.Count, IM.ColumnCount);
                    int             nvC       = 0;
                    foreach (int nRow in cluster)
                    {
                        imMatrixT.SetRow(nvC, IM.Row(nRow));
                        nvC++;
                    }
                    for (int c = 0; c < IM.ColumnCount; c++)
                    {
                        Vector <double> column = imMatrixT.Column(c);
                        int             Nin    = column.FindValue(IN);
                        int             Nout   = column.FindValue(OUT);
                        if (Nin > 0 && Nout > 0)
                        {
                            imMatrixU[r, c] = OUT;
                        }
                        else if (Nout > 0)
                        {
                            imMatrixU[r, c] = OUT;
                        }
                        else if (Nin > 0)
                        {
                            imMatrixU[r, c] = IN;
                        }
                        else
                        {
                            imMatrixU[r, c] = NOTHING;
                        }
                    }
                }
            }
            return(imMatrixU);
        }
示例#2
0
        private static List <int> ModelsInSCCFromIMM(IncidenceMatrix IM)
        {
            var modelsInSCC = new List <int>();

            for (int r = 0; r < IM.RowCount; r++)
            {
                if (FindValueInArray(IM.Row(r).ToArray(), ANY))
                {
                    modelsInSCC.Add(r);
                }
            }
            return(modelsInSCC);
        }
示例#3
0
        /// <summary>
        /// This is the first step of incidence matrix method. This function performs the operation described in chapter3.2.1 in [1]
        /// </summary>
        /// <param name="IM"></param>
        /// <param name="Noutvalr"></param>
        /// <param name="Noutvalc"></param>
        /// <param name="Activat"></param>
        private static void IncidenceMatrixFirstStep(IncidenceMatrix IM, double[] Noutvalr, double[] Noutvalc, bool Activat)
        {
            IncidenceMatrix IMstart;

            do
            {
                IMstart = IncidenceMatrix.Build.DenseOfMatrix(IM);
                var locations = IM.FindLocations(ANY);
                foreach ((int row, int col) in locations)
                {
                    double currentValr = IM.Row(row).MultiplyNonZeroVector();
                    double currentValc = IM.Column(col).MultiplyNonZeroVector();
                    // Coefficients in equations (1) to (4) in reference [1]
                    double Cvalr = Noutvalr[row] / currentValr;
                    double Cvalc = Noutvalc[col] / currentValc;
                    //checking for rows
                    double R2 = Log(Cvalr) / Log(IN);
                    double R3 = Log(Cvalr) / Log(OUT);
                    double C2 = Log(Cvalc) / Log(IN);
                    double C3 = Log(Cvalc) / Log(OUT);

                    if (IsInteger(R2) && !IsInteger(C3))                     // D1 in Fig. 1
                    {
                        IM[row, col] = IN;
                    }
                    else if (IsInteger(R3) && !IsInteger(C2))                     // D2 in Fig. 1
                    {
                        IM[row, col] = OUT;
                    }
                    else if (IsInteger(C2) && !IsInteger(R3))                     // D3 in Fig. 1
                    {
                        IM[row, col] = IN;
                    }
                    else if (IsInteger(C3) && !IsInteger(R2))
                    {
                        if (!Activat && (IM.Column(col).FindAnyValue() > 1))
                        {
                            IM[row, col] = OUT;
                        }
                        else if (Activat)
                        {
                            IM[row, col] = OUT;
                        }
                    }
                }
            } while (!IMstart.Equals(IM));
        }
示例#4
0
        /// <summary>
        /// This function identifies the Modified models (from imMatrixi and imMatrif) in the modelObjects, then creates a 'modified model subprocess' for each modified model,
        /// and therafter combines it with other models in the modelObjects and return it in a object array
        /// </summary>
        /// <param name="IMi"></param>
        /// <param name="IMf"></param>
        /// <param name="components"></param>
        /// <param name="data"></param>
        /// <param name="clusters"></param>
        /// <param name="name"></param>
        /// <returns></returns>
        private static WorkflowComponent[] CreateReversedModels(IncidenceMatrix IMi, IncidenceMatrix IMf, List <WorkflowComponent> components, List <Data> data, List <Cluster> clusters, string name)
        {
            var processedComponents = new WorkflowComponent[IMf.RowCount];

            for (int r = 0; r < IMi.RowCount; r++)
            {
                WorkflowComponent component = components[r];
                Vector <double>   row       = IMi.Row(r);
                if (!IMf.Row(r).CompareAssigned(row))
                {
                    List <int> inputIndices  = row.FindLocations(IN);
                    List <int> outputIndices = row.FindLocations(OUT);
                    var        inputs        = inputIndices.Select(i => data[i]).ToList();
                    var        outputs       = outputIndices.Select(i => data[i]).ToList();

                    if (component is Model model)
                    {
                        processedComponents[r] = model.Reverse(inputs, outputs);
                    }
                    else if (component is Workflow workflow)
                    {
                        var opts = new NewtonOptions()
                        {
                            MaxIterations = 20, DerivativeStep = new double[] { 0.01 }
                        };
                        var solver = new NewtonSolver(opts);
                        processedComponents[r] = new WorkflowGlobal($"{name}#GlobalWorkflow#{workflow.Name}", "", inputs, outputs, workflow.Components, workflow.Components, new List <ISolver>()
                        {
                            solver
                        });
                    }
                }
                else
                {
                    processedComponents[r] = components[r];
                }
            }
            return(processedComponents);
        }
示例#5
0
        /// <summary>
        /// This function adds additional varaibles as indpendent varaibles. This is done when the system is underdetermined and
        /// additional variables are required to solve it.
        /// </summary>
        /// <param name="IM"></param>
        /// <param name="Noutvalr"></param>
        /// <param name="Noutvalc"></param>
        private static void FillAsInput(IncidenceMatrix IM, double[] Noutvalr, double[] Noutvalc)
        {
            List <(int i, int j)> locations = IM.FindLocations(ANY);

            foreach ((int row, int col) in locations)
            {
                //% fills the ANYs with IN if IN has to be put in row and in column
                //% this make the variable in the column to be an input
                double currentValr = IM.Row(row).MultiplyNonZeroVector();
                double currentValc = IM.Column(col).MultiplyNonZeroVector();
                // Coefficients in equations (1) to (4) in reference [1]
                double Cvalr = Noutvalr[row] / currentValr;
                double Cvalc = Noutvalc[col] / currentValc;
                //checking for rows
                double R2 = Log(Cvalr) / Log(IN);
                double C3 = Log(Cvalc) / Log(OUT);

                if (IsInteger(R2) && IsInteger(C3))                 // D1 in Fig. 1
                {
                    IM[row, col] = IN;
                }
            }
        }
示例#6
0
 public static bool IsModelUnassigned(this IncidenceMatrix IM, int model) => IM.Row(model).FindValue(ANY) > 0;
示例#7
0
 public static int NOutputs(this IncidenceMatrix IM, int model) => IM.Row(model).FindValue(OUT);
示例#8
0
 public static int NInputs(this IncidenceMatrix IM, int model) => IM.Row(model).FindValue(IN);
示例#9
0
 public static int NVariables(this IncidenceMatrix IM, int model) => IM.Row(model).FindValue(ANY);
示例#10
0
        private static List <IncidenceMatrix> IncidenceExploreRecurse(IncidenceMatrix IMi, IncidenceMatrix IMf, double[] Noutvalr, double[] Noutvalc, List <IncidenceMatrix> IMlist, double minNReversed)
        {
            var IMset = new List <IncidenceMatrix>(1000);

            List <int> notAssigned = FindNotAssignedModels(IMi, IMf);
            List <int> reversed    = FindReversedModels(IMi, IMf);

            if (reversed.Count == 0)
            {
                reversed = new HashSet <int>(IMi.FindLocations(ANY).Select(l => l.i)).ToList();
            }

            for (int rev = 0; rev < reversed.Count; rev++)
            {
                int             r           = reversed[rev];
                Vector <double> row         = IMi.Row(r);
                List <int>      locations   = row.FindLocations(ANY);
                double          currentValr = row.MultiplyNonZeroVector();
                double          Cvalr       = Noutvalr[r] / currentValr;
                for (int l = 0; l < locations.Count; l++)
                {
                    int    c           = locations[l];
                    double currentValc = IMi.Column(c).MultiplyNonZeroVector();
                    double Cvalc       = Noutvalc[c] / currentValc;

                    double R2 = Log(Cvalr) / Log(IN);
                    double C2 = Log(Cvalc) / Log(IN);
                    if (!IsInteger(C2) && !IsInteger(R2))
                    {
                        IncidenceMatrix IMg = IncidenceMatrix.Build.DenseOfMatrix(IMi);
                        IMg[r, c] = OUT;
                        IncidenceMatrixFirstStep(IMg, Noutvalr, Noutvalc, true);
                        FillAsInput(IMg, Noutvalr, Noutvalc);

                        if (IMg.FindLocations(ANY).Count == 0)
                        {
                            int NRevModels = FindNReversed(IMi, IMg);

                            if (NRevModels < minNReversed)
                            {
                                IMlist.Clear();
                                IMlist.Add(IMg);
                                minNReversed = NRevModels;
                            }
                            else if (NRevModels == minNReversed)
                            {
                                IMlist.Add(IMg);
                            }
                            else
                            {
                                // do nothing as inspected incidence already has more rev models than those stored.
                            }

                            if (IMlist.Count >= MaxWorkflowAlternatives || explorationWatch.ElapsedMilliseconds > MaxEllapsedTime)
                            {
                                return(IMlist);
                            }
                        }
                        else
                        {
                            IncidenceExplore(IMg, IMf, Noutvalr, Noutvalc);
                        }
                    }
                }
            }

            if (IMlist.Count == 0)
            {
                throw new ArgumentException(NoIMsFoundErrorMessage);
            }

            return(IMlist);
        }