Beispiel #1
0
        /// <summary>
        /// Determines how many child instances will eventually be generated after running all division rules. For each child
        /// instance, it generates KPChildInstance (sub class of MInstance) object and adds them as MInstance(regular
        /// instances) to MType. For each MInstance (including KPChildInstances) an SMV module will be generated.
        /// </summary>
        /// <param name="type">KP type (MType)</param>
        /// <returns>List of child instance of KPChildInstance type</returns>
        internal static List <KPChildInstance> generateKPChildInstances(MType type)
        {
            List <KPChildInstance> kpChildInstances = new List <KPChildInstance>();

            //After all divisions, how many child will be generated.
            int totalChildNumber = 1;
            ExecutionStrategy eS = type.ExecutionStrategy;

            while (eS != null)
            {
                foreach (var rule in eS.Rules)
                {
                    if (rule.Type == RuleType.MEMBRANE_DIVISION)
                    {
                        DivisionRule divisionRule = (DivisionRule)rule;
                        totalChildNumber *= divisionRule.Rhs.Count;
                    }
                }
                eS = eS.Next;
            }
            //for each parent instance, totalChildNumber, child instance will be generated
            foreach (MInstance kpInstance in type.Instances)
            {
                for (int childCount = 1; childCount <= totalChildNumber; childCount++)
                {
                    KPChildInstance kpChildInstance = new KPChildInstance(kpInstance);
                    kpChildInstance.Order = childCount;
                    kpChildInstance.Name  = kpInstance.Name + SMVPreFix.CHILD + childCount;
                    kpChildInstances.Add(kpChildInstance);
                }
            }
            return(kpChildInstances);
        }
Beispiel #2
0
        /// <summary>
        /// It recursively buffers the InstanceBlueprint division rules (in result list) for all child instances, in order to
        /// get the result of only relevant child, we use childOrderTracer which is kind of the ID of child instance, if the
        /// recursion arrives this child then performs calculations over buffered @param result.
        /// </summary>
        /// <param name="divisionRules"></param>
        /// <param name="ruleCount"></param>
        /// <param name="result">Holds list of InstanceBlueprint of division rules</param>
        private static void getRulePermutation(List <KpCore.Rule> divisionRules, int ruleCount, List <InstanceBlueprint> result)
        {
            //if it completes on cycle of recursion
            if (ruleCount == divisionRules.Count)
            {
                //check if this cycle belongs to requested child instance
                if (childOrderTracer == (kPInstance as KPChildInstance).Order)
                {
                    //then perform calculation
                    calculateValuesOfDivisionVariables(divisionRules, result);
                }
                childOrderTracer++;
                return;
            }
            DivisionRule divisionRule = (DivisionRule)divisionRules.ElementAt(ruleCount);
            int          compartCount = divisionRule.Rhs.Count;

            ruleCount++;
            for (int j = 0; j < compartCount; j++)
            {
                InstanceBlueprint compartment = divisionRule.Rhs.ElementAt(j);
                int index = ruleCount - 1;
                if (result.Count < ruleCount)
                {
                    result.Insert(index, compartment);
                }
                else
                {
                    result.RemoveAt(index);
                    result.Insert(index, compartment);
                }
                getRulePermutation(divisionRules, ruleCount, result);
            }
        }
Beispiel #3
0
        private static void getRulePermutation(ParentInstance parentInstance, List <KpCore.Rule> divisionRules, int ruleCount, List <InstanceBlueprint> result)
        {
            if (ruleCount == divisionRules.Count)
            {
                formDivisionInstance(parentInstance, divisionRules, result);
                return;
            }
            DivisionRule divisionRule = (DivisionRule)divisionRules.ElementAt(ruleCount);
            int          compartCount = divisionRule.Rhs.Count;

            ruleCount++;
            for (int j = 0; j < compartCount; j++)
            {
                InstanceBlueprint compartment = divisionRule.Rhs.ElementAt(j);
                int index = ruleCount - 1;
                if (result.Count < ruleCount)
                {
                    result.Insert(index, compartment);
                }
                else
                {
                    result.RemoveAt(index);
                    result.Insert(index, compartment);
                }
                getRulePermutation(parentInstance, divisionRules, ruleCount, result);
            }
        }
        public object VisitRuleRightHandSide(KpLinguaParser.RuleRightHandSideContext context)
        {
            var rule = default(ConsumerRule);

            var ruleMultisetContexts   = context.ruleMultiset();
            var divisionContexts       = context.division();
            var dissolutionContext     = context.dissolution();
            var linkCreationContext    = context.linkCreation();
            var linkDestructionContext = context.linkDestruction();

            if (ruleMultisetContexts != null)
            {
                var rewritingRule = default(RewritingRule);

                if (ruleMultisetContexts.Any(rm => rm.targetedMultiset() != null))
                {
                    var rewriteCommunicationRule = new RewriteCommunicationRule();
                    var targetedMultisets        = ruleMultisetContexts.Where(rm => rm.targetedMultiset() != null).Select(rm => rm.targetedMultiset().Accept(this) as TargetedMultiset);
                    rewriteCommunicationRule.AddRhs(targetedMultisets.ToDictionary(tm => tm.Target));

                    rewritingRule = rewriteCommunicationRule;
                }
                else
                {
                    rewritingRule = new RewritingRule();
                }

                var multisets = ruleMultisetContexts.Where(rm => rm.nonEmptyMultiset() != null).Select(rm => rm.nonEmptyMultiset().Accept(this) as Multiset);
                foreach (var multiset in multisets)
                {
                    rewritingRule.AddRhs(multiset);
                }

                rule = rewritingRule;
            }
            else if (divisionContexts != null)
            {
                var divisionRule = new DivisionRule();

                foreach (var divisionContext in divisionContexts)
                {
                    divisionRule.Rhs.Add(divisionContext.Accept(this) as InstanceBlueprint);
                }

                rule = divisionRule;
            }
            else if (dissolutionContext != null)
            {
                rule = dissolutionContext.Accept(this) as DissolutionRule;
            }
            else if (linkCreationContext != null)
            {
            }
            else if (linkDestructionContext != null)
            {
            }

            return(rule);
        }
Beispiel #5
0
        private static int getTotalAmountOfDivisionVar(IVar variable, List <KpCore.Rule> divisionRules, List <InstanceBlueprint> result)
        {
            int    totalAmount   = 0;
            bool   isFirstParent = true;
            string typeName      = "";

            foreach (InstanceBlueprint item in result)
            {
                typeName = item.Type.Name;
                int childValue = 0;
                int leftValue  = 0;
                foreach (var divisionRule in divisionRules)
                {
                    DivisionRule divRule = (DivisionRule)divisionRule;
                    if (divRule.Rhs.Contains(item))
                    {
                        Multiset leftOfRule = divRule.Lhs;
                        foreach (var leftObj in leftOfRule.Objects)
                        {
                            if (leftObj.Equals(variable.Name))
                            {
                                if (isFirstParent)
                                {
                                    totalAmount   = leftOfRule[leftObj];
                                    isFirstParent = false;
                                }
                                leftValue = leftOfRule[leftObj];
                            }
                        }
                    }
                }
                Multiset ms = item.Multiset;
                foreach (var obj in ms.Objects)
                {
                    if (obj.Equals(variable.Name))
                    {
                        childValue = ms[obj];
                    }
                }

                totalAmount = totalAmount - leftValue + childValue;
            }
            //update max value.
            if (variable.Type is BoundInt)
            {
                (variable.Type as BoundInt).UpperBound = Math.Max((variable.Type as BoundInt).UpperBound, totalAmount);
            }

            return(totalAmount);
        }
Beispiel #6
0
        private static void buildDivisionVariables(NuSMV.Module module, KPsystem kpSystem, KpCore.MType type, int strategyIndex, KpCore.Rule rule)
        {
            DivisionRule divisionRule = (DivisionRule)rule;

            foreach (var leftHRule in divisionRule.Lhs)
            {
                Variable variable = new Variable(leftHRule.Key);
                if (!module.Variables.Contains(variable))
                {
                    variable.Type      = new BoundInt(0, setMax(kpSystem, type, module, variable));
                    variable.Behaviour = VariableBehaviour.REWRITING;
                    variable.Init      = setOrUpdateInit(module, variable);
                    module.Variables.Add(variable);
                }
                else
                {
                    //if variable exists then update the upperbound value.
                    variable = (Variable)module.Variables.First(item => item.Name.Equals(leftHRule.Key));
                }
                //add result of rule to caseline
                BRulesStandardVar.addCaseLineToStandardVariable(variable, rule, module, strategyIndex);
            }

            foreach (InstanceBlueprint compartment in divisionRule.Rhs)
            {
                MType compType = compartment.Type;
                if (type.Name.Equals(compType.Name))
                {
                    Multiset ms = compartment.Multiset;
                    foreach (var obj in ms.Objects)
                    {
                        Variable variable = new Variable(obj);
                        if (!module.Variables.Contains(variable))
                        {
                            variable.Type      = new BoundInt(0, setMax(kpSystem, compType, module, variable));
                            variable.Behaviour = VariableBehaviour.DIVISION;
                            variable.Init      = setOrUpdateInit(module, variable);
                            module.Variables.Add(variable);
                        }
                        else
                        {
                            variable           = (Variable)module.Variables.First(item => item.Name.Equals(obj));
                            variable.Behaviour = VariableBehaviour.DIVISION;
                        }
                    }
                }
            }
            // add rule to status variable
            BRulesCustomVar.addRuleToStatusVariable(rule, module, strategyIndex);
        }
        public static string Rule(Rule r)
        {
            StringBuilder buf = new StringBuilder();

            if (r.IsGuarded)
            {
                buf.Append(Guard(r.Guard)).Append(": ");
            }

            if (r is ConsumerRule)
            {
                buf.Append(Multiset((r as ConsumerRule).Lhs)).Append(" -> ");
                switch (r.Type)
                {
                case RuleType.MULTISET_REWRITING: {
                    buf.Append(Multiset((r as RewritingRule).Rhs));
                } break;

                case RuleType.REWRITE_COMMUNICATION: {
                    RewriteCommunicationRule rcr = r as RewriteCommunicationRule;
                    if (!rcr.Rhs.IsEmpty())
                    {
                        buf.Append(Multiset(rcr.Rhs)).Append(", ");
                    }
                    int tCount = rcr.TargetRhs.Count;
                    int i      = 1;
                    foreach (KeyValuePair <IInstanceIdentifier, TargetedMultiset> kv in rcr.TargetRhs)
                    {
                        if (kv.Key is InstanceIdentifier)
                        {
                            if ((kv.Key as InstanceIdentifier).Indicator == InstanceIndicator.TYPE)
                            {
                                buf.AppendFormat("{{{0}}}({1})", Multiset(kv.Value.Multiset), (kv.Key as InstanceIdentifier).Value);
                                if (i < tCount)
                                {
                                    buf.Append(", ");
                                }
                            }
                        }
                    }
                } break;

                case RuleType.MEMBRANE_DISSOLUTION: {
                    buf.Append("#");
                } break;

                case RuleType.MEMBRANE_DIVISION: {
                    DivisionRule dr = r as DivisionRule;
                    foreach (InstanceBlueprint ib in dr.Rhs)
                    {
                        buf.AppendFormat("[{0}]({1})", Multiset(ib.Multiset, true), ib.Type.Name);
                    }
                } break;

                case RuleType.LINK_CREATION: {
                    LinkRule lr = r as LinkRule;
                    if (lr.Target is InstanceIdentifier)
                    {
                        InstanceIdentifier iid = lr.Target as InstanceIdentifier;
                        if (iid.Indicator == InstanceIndicator.TYPE)
                        {
                            buf.AppendFormat("- ({0})", iid.Value);
                        }
                    }
                } break;

                case RuleType.LINK_DESTRUCTION: {
                    LinkRule lr = r as LinkRule;
                    if (lr.Target is InstanceIdentifier)
                    {
                        InstanceIdentifier iid = lr.Target as InstanceIdentifier;
                        if (iid.Indicator == InstanceIndicator.TYPE)
                        {
                            buf.AppendFormat("\\- ({0})", iid.Value);
                        }
                    }
                } break;
                }
            }

            return(buf.ToString());
        }
Beispiel #8
0
        public static string TranslateRule(Rule r, MType container = null)
        {
            StringBuilder buf = new StringBuilder();

            if (r is ConsumerRule)
            {
                ConsumerRule rule = r as ConsumerRule;
                if (r.IsGuarded)
                {
                    buf.Append(TranslateGuard(r.Guard));
                    buf.Append(": ");
                }

                buf.Append(TranslateMultiset(rule.Lhs));
                buf.Append(" -> ");
                switch (r.Type)
                {
                    case RuleType.MULTISET_REWRITING:
                        {
                            buf.Append(TranslateMultiset((r as RewritingRule).Rhs));
                        } break;
                    case RuleType.REWRITE_COMMUNICATION:
                        {
                            RewriteCommunicationRule rcr = r as RewriteCommunicationRule;
                            if (!rcr.Rhs.IsEmpty())
                            {
                                buf.Append(TranslateMultiset(rcr.Rhs));
                                if (rcr.TargetRhs.Count > 0)
                                {
                                    buf.Append(", ");
                                }
                            }
                            buf.Append(TranslateTargetedMultiset(rcr.TargetRhs.Values));
                        } break;
                    case RuleType.MEMBRANE_DISSOLUTION:
                        {
                            buf.Append("#");
                        } break;
                    case RuleType.LINK_CREATION:
                        {
                            LinkRule lr = r as LinkRule;
                            if (lr.Target is InstanceIdentifier)
                            {
                                InstanceIdentifier iid = lr.Target as InstanceIdentifier;
                                if (iid.Indicator == InstanceIndicator.TYPE)
                                {
                                    buf.Append("-(").Append(iid.Value).Append(")");
                                }
                            }
                        } break;
                    case RuleType.LINK_DESTRUCTION:
                        {
                            LinkRule lr = r as LinkRule;
                            if (lr.Target is InstanceIdentifier)
                            {
                                InstanceIdentifier iid = lr.Target as InstanceIdentifier;
                                if (iid.Indicator == InstanceIndicator.TYPE)
                                {
                                    buf.Append("\\-(").Append(iid.Value).Append(")");
                                }
                            }
                        } break;
                    case RuleType.MEMBRANE_DIVISION:
                        {
                            DivisionRule dr = r as DivisionRule;
                            foreach (InstanceBlueprint ib in dr.Rhs)
                            {
                                buf.Append("[");
                                if (!ib.Multiset.IsEmpty())
                                {
                                    buf.Append(TranslateMultiset(ib.Multiset));
                                }
                                buf.Append("]");
                                if (container != null)
                                {
                                    if (container.Name == ib.Type.Name)
                                    {
                                        continue;
                                    }
                                }
                                buf.Append("(").Append(ib.Type.Name).Append(")");
                            }
                        } break;
                }

                buf.Append(" .");
            }

            return buf.ToString();
        }
Beispiel #9
0
        private void writeRule(Rule rule)
        {
            owt.Write("{");
            bool pItem = writePItem(rule);

            if (!rule.IsEmpty())
            {
                if (pItem)
                {
                    owt.Write(", ");
                }

                if (rule.IsGuarded)
                {
                    owt.Write("\"guard\":");
                    writeGuard(rule.Guard);
                    owt.Write(", ");
                }

                if (rule.Type == RuleType.CONSUMER)
                {
                    owt.Write("\"lhs\":");
                    writeMultiset((rule as ConsumerRule).Lhs);
                }
                else if (rule.Type == RuleType.MULTISET_REWRITING)
                {
                    RewritingRule r = rule as RewritingRule;
                    owt.Write("\"lhs\":");
                    writeMultiset(r.Lhs);
                    owt.Write(", \"rhs\":");
                    writeMultiset(r.Rhs);
                }
                else if (rule.Type == RuleType.REWRITE_COMMUNICATION)
                {
                    RewriteCommunicationRule r = rule as RewriteCommunicationRule;
                    owt.Write("\"lhs\":");
                    writeMultiset(r.Lhs);
                    owt.Write(", \"rhs\":");
                    writeMultiset(r.Rhs);
                    owt.Write(", \"targetRhs\":[");
                    int i = 1;
                    foreach (TargetedMultiset tm in r.TargetRhs.Values)
                    {
                        writeTargetedMultiset(tm);
                        if (i++ < r.TargetRhs.Count)
                        {
                            owt.Write(", ");
                        }
                    }
                    owt.Write("]");
                }
                else if (rule.Type == RuleType.MEMBRANE_DIVISION)
                {
                    DivisionRule r = rule as DivisionRule;
                    owt.Write("\"lhs\":");
                    writeMultiset(r.Lhs);
                    owt.Write(", \"instances\":[");
                    int i = 1;
                    foreach (InstanceBlueprint ib in r.Rhs)
                    {
                        writeInstanceBlueprint(ib);
                        if (i++ < r.Rhs.Count)
                        {
                            owt.Write(", ");
                        }
                    }
                    owt.Write("]");
                }
                else if (rule.Type == RuleType.LINK_CREATION)
                {
                    LinkRule r = rule as LinkRule;
                    owt.Write("\"lhs\":");
                    writeMultiset(r.Lhs);
                    owt.Write(",\"linkCreate\":");
                    writeInstanceIdentifier(r.Target);
                }
                else if (rule.Type == RuleType.LINK_DESTRUCTION)
                {
                    LinkRule r = rule as LinkRule;
                    owt.Write("\"lhs\":");
                    writeMultiset(r.Lhs);
                    owt.Write(",\"linkDestroy\":");
                    writeInstanceIdentifier(r.Target);
                }
                else if (rule.Type == RuleType.MEMBRANE_DISSOLUTION)
                {
                    DissolutionRule r = rule as DissolutionRule;
                    owt.Write("\"lhs\":");
                    writeMultiset(r.Lhs);
                    owt.Write(", \"dissolve\": true");
                }
            }

            owt.Write("}");
        }
        private Rule readRule(XPathNavigator nav)
        {
            ConsumerRule rule = null;

            XPathNavigator rhsNav = nav.SelectSingleNode("rhs");

            if (rhsNav != null)
            {
                Multiset          m = readMultiset(rhsNav);
                XPathNodeIterator div;
                if (m.IsEmpty())
                {
                    //then we can have structure changing rules
                    div = rhsNav.SelectChildren("instance", String.Empty);
                    if (div.Count > 0)
                    {
                        DivisionRule r = new DivisionRule();
                        while (div.MoveNext())
                        {
                            string            mtype = div.Current.GetAttribute("mtype", String.Empty);
                            InstanceBlueprint ib    = null;
                            if (String.IsNullOrEmpty(mtype))
                            {
                                ib = new InstanceBlueprint(currentType);
                            }
                            else
                            {
                                ib = new InstanceBlueprint(kp[mtype]);
                            }
                            readMultiset(div.Current, ib.Multiset);
                            r.Rhs.Add(ib);
                        }
                        rule = r;
                    }
                    else
                    {
                        XPathNavigator v;
                        v = rhsNav.SelectSingleNode("linkCreate");
                        if (v == null)
                        {
                            v = rhsNav.SelectSingleNode("linkDestroy");
                            if (v == null)
                            {
                                v = rhsNav.SelectSingleNode("dissolve");
                                if (v != null)
                                {
                                    rule = new DissolutionRule();
                                }
                            }
                            else
                            {
                                rule = LinkRule.LinkDestroy(readInstanceIdentifier(v));
                            }
                        }
                        else
                        {
                            rule = LinkRule.LinkCreate(readInstanceIdentifier(v));
                        }
                    }
                }

                if (rule == null)
                {
                    div = rhsNav.SelectChildren("target", String.Empty);
                    if (div.Count > 0)
                    {
                        RewriteCommunicationRule rcr = new RewriteCommunicationRule();
                        rcr.Rhs.Add(m);
                        while (div.MoveNext())
                        {
                            TargetedMultiset tm  = readTargetedMultiset(div.Current);
                            TargetedMultiset otm = null;
                            rcr.TargetRhs.TryGetValue(tm.Target, out otm);
                            if (otm == null)
                            {
                                rcr.TargetRhs.Add(tm.Target, tm);
                            }
                            else
                            {
                                otm.Multiset.Add(tm.Multiset);
                            }
                        }
                        rule = rcr;
                    }
                    else if (m != null)
                    {
                        rule = new RewritingRule();
                        (rule as RewritingRule).Rhs.Add(m);
                    }
                }
            }

            if (rule == null)
            {
                rule = new ConsumerRule();
            }
            readPItem(nav, rule);
            rule.Guard = readGuard(nav.SelectSingleNode("guard"));
            readMultiset(nav.SelectSingleNode("lhs"), rule.Lhs);

            return(rule);
        }
Beispiel #11
0
        internal void build()
        {
            int id;

            MaxLinks        = 0;
            MaxDivisionRate = 0;
            foreach (MInstance instance in mtype.Instances)
            {
                id = nextInstanceId();
                MInstanceMeta im = new MInstanceMeta(this, instance, id);
                iMeta.Add(id, im);
                kpmm.InstanceRegistry.Add(instance, im);
                AddSymbols(instance.Multiset.Objects);
                if (instance.Connections.Count > MaxLinks)
                {
                    MaxLinks = instance.Connections.Count;
                }
            }
            instances = mtype.Instances.ToArray();

            List <Rule>       rs       = new List <Rule>();
            ExecutionStrategy strategy = mtype.ExecutionStrategy;

            while (strategy != null)
            {
                foreach (Rule r in strategy.Rules)
                {
                    id = nextRuleId();
                    RuleMeta rm = new RuleMeta(this, r, id);
                    rMeta.Add(id, rm);
                    rs.Add(r);
                    kpmm.RuleRegistry[r] = rm;
                    if (r.IsGuarded)
                    {
                        extractGuardAlphabet(r.Guard);
                    }

                    switch (r.Type)
                    {
                    case RuleType.MULTISET_REWRITING: {
                        AddSymbols((r as RewritingRule).Lhs.Objects);
                        AddSymbols((r as RewritingRule).Rhs.Objects);
                    } break;

                    case RuleType.REWRITE_COMMUNICATION: {
                        RewriteCommunicationRule rc = r as RewriteCommunicationRule;
                        AddSymbols(rc.Lhs.Objects);
                        AddSymbols(rc.Rhs.Objects);
                        foreach (TargetedMultiset tarm in rc.TargetRhs.Values)
                        {
                            if (tarm.Target is InstanceIdentifier)
                            {
                                InstanceIdentifier iId = tarm.Target as InstanceIdentifier;
                                if (iId.Indicator == InstanceIndicator.TYPE)
                                {
                                    AddSymbols(tarm.Multiset.Objects, iId.Value);
                                    //add interest in this connection
                                    interests.Add(kpmm.GetTypeMetaByName(iId.Value, true));
                                }
                            }
                        }
                    } break;

                    case RuleType.MEMBRANE_DIVISION: {
                        DivisionRule dr = r as DivisionRule;
                        AddSymbols(dr.Lhs.Objects);
                        foreach (InstanceBlueprint ib in dr.Rhs)
                        {
                            AddSymbols(ib.Multiset.Objects, ib.Type.Name);
                            if (ib.Type == MType)
                            {
                                MaxDivisionRate++;
                                divisibleTypes.Add(this);
                            }
                            else
                            {
                                kpmm.GetTypeMetaByName(ib.Type.Name).MaxDivisionRate++;
                                divisibleTypes.Add(kpmm.GetTypeMetaByType(ib.Type));
                            }
                        }
                    } break;

                    default: {
                        if (r is LinkRule)
                        {
                            LinkRule lr = r as LinkRule;
                            AddSymbols(lr.Lhs.Objects);
                            if (lr.Target is InstanceIdentifier)
                            {
                                InstanceIdentifier iid = lr.Target as InstanceIdentifier;
                                if (iid.Indicator == InstanceIndicator.TYPE)
                                {
                                    MTypeMeta mtm = kpmm.GetTypeMetaByName(iid.Value, true);
                                    interests.Add(mtm);
                                    if (lr.Type == RuleType.LINK_CREATION)
                                    {
                                        mayConnectTo.Add(mtm);
                                    }
                                }
                            }
                        }
                        else if (r is ConsumerRule)
                        {
                            AddSymbols((r as ConsumerRule).Lhs.Objects);
                        }
                    } break;
                    }
                    HasCommunication   = HasCommunication || r.Type == RuleType.REWRITE_COMMUNICATION;
                    HasDivision        = HasDivision || r.Type == RuleType.MEMBRANE_DIVISION;
                    HasDissolution     = HasDissolution || r.Type == RuleType.MEMBRANE_DISSOLUTION;
                    HasLinkCreation    = HasLinkCreation || r.Type == RuleType.LINK_CREATION;
                    HasLinkDestruction = HasLinkDestruction || r.Type == RuleType.LINK_DESTRUCTION;
                }
                strategy = strategy.Next;
            }
            rules = rs.ToArray();
        }
Beispiel #12
0
        /// <summary>
        /// if variable has NOT been set by XML file then set max automatically
        /// </summary>
        /// <param name="kpSystem"></param>
        /// <param name="myType"></param>
        /// <param name="module"></param>
        /// <param name="variable"></param>
        /// <returns></returns>
        private static int setMax(KPsystem kpSystem, MType myType, NuSMV.Module module, IVar variable)
        {
            int maxVal = 0;

            foreach (var type in kpSystem.Types)
            {
                ExecutionStrategy eS = type.ExecutionStrategy;
                while (eS != null)
                {
                    //Inside this type
                    if (myType.Name.Equals(type.Name))
                    {
                        foreach (var rule in eS.Rules)
                        {
                            //Normal variable
                            if (rule.Type == RuleType.MULTISET_REWRITING)
                            {
                                RewritingRule rwr = (RewritingRule)rule;
                                foreach (var leftHRule in rwr.Lhs)
                                {
                                    if (variable.Name.Equals(leftHRule.Key))
                                    {
                                        maxVal = Math.Max(maxVal, leftHRule.Value);
                                    }
                                }
                                foreach (var rigthHRule in rwr.Rhs)
                                {
                                    if (variable.Name.Equals(rigthHRule.Key))
                                    {
                                        maxVal = Math.Max(maxVal, rigthHRule.Value);
                                    }
                                }
                            }
                            // Communication Var
                            else if (rule.Type == RuleType.REWRITE_COMMUNICATION)
                            {
                                RewriteCommunicationRule rcr = (RewriteCommunicationRule)rule;
                                foreach (var leftHRule in rcr.Lhs)
                                {
                                    if (variable.Name.Equals(leftHRule.Key))
                                    {
                                        maxVal = Math.Max(maxVal, leftHRule.Value);
                                    }
                                }
                            }
                            else if (rule.Type == RuleType.MEMBRANE_DIVISION)
                            {
                                DivisionRule divisionRule = (DivisionRule)rule;
                                foreach (var leftHRule in divisionRule.Lhs)
                                {
                                    if (variable.Name.Equals(leftHRule.Key))
                                    {
                                        maxVal = Math.Max(maxVal, leftHRule.Value);
                                    }
                                }
                                foreach (InstanceBlueprint compartment in divisionRule.Rhs)
                                {
                                    MType compType = compartment.Type;
                                    if (myType.Name.Equals(compType.Name))
                                    {
                                        Multiset ms = compartment.Multiset;
                                        foreach (var obj in ms.Objects)
                                        {
                                            if (variable.Name.Equals(obj))
                                            {
                                                maxVal = Math.Max(maxVal, ms[obj]);
                                            }
                                        }
                                    }
                                }
                            }
                            else if (rule.Type == RuleType.MEMBRANE_DISSOLUTION)
                            {
                                DissolutionRule dissolutionRule = (DissolutionRule)rule;
                                foreach (var leftHRule in dissolutionRule.Lhs)
                                {
                                    if (variable.Name.Equals(leftHRule.Key))
                                    {
                                        maxVal = Math.Max(maxVal, leftHRule.Value);
                                    }
                                }
                            }
                        }
                    }
                    //Inside communication rule of other types
                    else
                    {
                        foreach (var rule in eS.Rules)
                        {
                            if (rule.Type == RuleType.REWRITE_COMMUNICATION)
                            {
                                RewriteCommunicationRule rcr = (RewriteCommunicationRule)rule;
                                foreach (var target in rcr.TargetRhs.Values)
                                {
                                    TargetedMultiset   tg         = (TargetedMultiset)target;
                                    InstanceIdentifier identifier = (InstanceIdentifier)tg.Target;
                                    if (myType.Name.Equals(identifier.Value))
                                    {
                                        Multiset ms = tg.Multiset;
                                        foreach (var rightVar in ms.Objects)
                                        {
                                            if (variable.Name.Equals(rightVar))
                                            {
                                                maxVal = Math.Max(maxVal, ms[rightVar]);
                                            }
                                        }
                                    }
                                }
                            }
                            else if (rule.Type == RuleType.MEMBRANE_DIVISION)
                            {
                                DivisionRule divisionRule = (DivisionRule)rule;
                                foreach (InstanceBlueprint compartment in divisionRule.Rhs)
                                {
                                    MType compType = compartment.Type;
                                    if (myType.Name.Equals(compType.Name))
                                    {
                                        Multiset ms = compartment.Multiset;
                                        foreach (var obj in ms.Objects)
                                        {
                                            if (variable.Name.Equals(obj))
                                            {
                                                maxVal = Math.Max(maxVal, ms[obj]);
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }
                    eS = eS.Next;
                }
                //also compare parameter values
                foreach (var instance in type.Instances)
                {
                    foreach (var param in instance.Multiset.Objects)
                    {
                        if (variable.Name.Equals(param))
                        {
                            maxVal = Math.Max(maxVal, instance.Multiset[param]);
                        }
                    }
                }
            }
            return(maxVal);
        }
Beispiel #13
0
        public KPsystem Run()
        {
            KpSimulationStep simStep = new KpSimulationStep()
            {
                KPsystem = kp, Step = step
            };

            if (SimulationStarted != null)
            {
                SimulationStarted(kp);
            }

            List <ActiveInstance>    activeInstances  = new List <ActiveInstance>();
            List <ActiveInstance>    targetSelections = new List <ActiveInstance>();
            HashSet <ActiveInstance> deadCells        = new HashSet <ActiveInstance>();

            while (!isHalted && step <= endStep)
            {
                rulesApplied = 0;
                bool advanceStrategyBlock = false;
                bool endStepForInstance   = false;

                bool dissolutionRuleApplied = false;
                bool divisionRuleApplied    = false;
                bool linkRuleApplied        = false;

                activeInstances.AddRange(allOperationalInstances);
                int aiCount = activeInstances.Count;

                while (aiCount > 0)
                {
                    //reset instance flags
                    advanceStrategyBlock = false;
                    endStepForInstance   = false;

                    //select an instance
                    ActiveInstance selectedInstance = activeInstances[rand.Next(aiCount)];

                    ExecutionStrategy ex = selectedInstance.CurrentStrategySegment;

                    //this can only happen if the rule set was set to empty
                    if (selectedInstance.ApplicableRules.Count > 0)
                    {
                        Rule selectedRule     = null;
                        bool isRuleApplicable = true;
                        if (ex.Operator == StrategyOperator.SEQUENCE)
                        {
                            selectedRule = selectedInstance.ApplicableRules.First();
                            if (selectedRule.IsGuarded)
                            {
                                if (!selectedRule.Guard.IsSatisfiedBy(selectedInstance.Instance.Multiset))
                                {
                                    isRuleApplicable = false;
                                }
                                else if (selectedInstance.FlagStructureRuleApplied)
                                {
                                    if (selectedRule.IsStructureChangingRule())
                                    {
                                        isRuleApplicable = false;
                                    }
                                }
                            }
                        }
                        else
                        {
                            int selectedIndex = 0;
                            int arCount       = selectedInstance.ApplicableRules.Count;

                            if (ex.Operator == StrategyOperator.ARBITRARY)
                            {
                                selectedIndex = rand.Next(arCount + 1);
                            }
                            else
                            {
                                selectedIndex = rand.Next(arCount);
                            }

                            if (selectedIndex == arCount)
                            {
                                //this essentially means "skip this block" - always in an arbitrary block, never elsewhere
                                selectedRule     = null;
                                isRuleApplicable = false;
                            }
                            else
                            {
                                selectedRule = selectedInstance.ApplicableRules[selectedIndex];
                                if (selectedInstance.FlagStructureRuleApplied)
                                {
                                    if (selectedRule.IsStructureChangingRule())
                                    {
                                        isRuleApplicable = false;
                                    }
                                }
                            }
                        }

                        if (isRuleApplicable)
                        {
                            if (selectedRule is ConsumerRule)
                            {
                                if ((selectedRule as ConsumerRule).Lhs > selectedInstance.Instance.Multiset)
                                {
                                    isRuleApplicable = false;
                                }
                            }
                        }

                        //At this point, the isRuleApplicable basically confirms that no structure rule has been applied thus far
                        //if the selected rule requires this, if guarded, the guard of the selected rule holds and
                        //the left hand multiset is contained in the instance multiset
                        if (isRuleApplicable)
                        {
                            switch (selectedRule.Type)
                            {
                            case RuleType.REWRITE_COMMUNICATION: {
                                RewriteCommunicationRule rcr = selectedRule as RewriteCommunicationRule;
                                foreach (KeyValuePair <IInstanceIdentifier, TargetedMultiset> kv in rcr.TargetRhs)
                                {
                                    if (kv.Key is InstanceIdentifier)
                                    {
                                        InstanceIdentifier iid = kv.Key as InstanceIdentifier;
                                        if (iid.Indicator == InstanceIndicator.TYPE)
                                        {
                                            IndexedMType targetType = indexedTypesByName[iid.Value];
                                            int          cCount     = selectedInstance.ConnectionCount(targetType);
                                            if (cCount > 0)
                                            {
                                                ActiveInstance selectedTarget = selectedInstance.GetTargetAtIndex(rand.Next(cCount), targetType);
                                                selectedTarget.CommunicatedMultiset = kv.Value.Multiset;
                                                targetSelections.Add(selectedTarget);
                                            }
                                            else
                                            {
                                                isRuleApplicable = false;
                                                break;
                                            }
                                        }
                                    }
                                }
                                if (isRuleApplicable)
                                {
                                    selectedInstance.Instance.Multiset.Subtract(rcr.Lhs);
                                    selectedInstance.Buffer.Add(rcr.Rhs);
                                    ruleApplied(selectedRule, selectedInstance.Instance);
                                    foreach (ActiveInstance ai in targetSelections)
                                    {
                                        if (step >= startStep)
                                        {
                                            if (recordTargetSelection)
                                            {
                                                if (TargetSelected != null)
                                                {
                                                    TargetSelected(ai.Instance, ai.Type, selectedRule);
                                                }
                                            }
                                        }
                                        ai.CommitCommunication();
                                    }
                                }
                                else
                                {
                                    foreach (ActiveInstance ai in targetSelections)
                                    {
                                        ai.ResetCommunication();
                                    }
                                }
                                targetSelections.Clear();
                            } break;

                            case RuleType.MULTISET_REWRITING: {
                                ruleApplied(selectedRule, selectedInstance.Instance);
                                selectedInstance.Instance.Multiset.Subtract((selectedRule as ConsumerRule).Lhs);
                                selectedInstance.Buffer.Add((selectedRule as RewritingRule).Rhs);
                            } break;

                            case RuleType.MEMBRANE_DISSOLUTION: {
                                ruleApplied(selectedRule, selectedInstance.Instance);
                                dissolutionRuleApplied         = true;
                                selectedInstance.FlagDissolved = true;
                                selectedInstance.Instance.Multiset.Subtract((selectedRule as ConsumerRule).Lhs);
                            } break;

                            case RuleType.LINK_CREATION: {
                                LinkRule lr = selectedRule as LinkRule;
                                if (lr.Target is InstanceIdentifier)
                                {
                                    string         typeName       = (lr.Target as InstanceIdentifier).Value;
                                    IndexedMType   targetType     = indexedTypesByName[typeName];
                                    ActiveInstance selectedTarget = null;
                                    //check if there is a link-free instance we can connect to
                                    int freeLinkCount = targetType.Instances.Count - selectedInstance.ConnectionCount(targetType);
                                    if (freeLinkCount > 0)
                                    {
                                        int selection = rand.Next(freeLinkCount);
                                        int i         = 0;
                                        foreach (ActiveInstance ai in targetType.Instances)
                                        {
                                            if (!selectedInstance.IsConnectedTo(ai))
                                            {
                                                if (i++ == selection)
                                                {
                                                    selectedTarget = ai;
                                                }
                                            }
                                        }

                                        selectedInstance.Instance.Multiset.Subtract(lr.Lhs);
                                        ruleApplied(selectedRule, selectedInstance.Instance);
                                        linkRuleApplied = true;
                                        //selected target can't be null here
                                        selectedInstance.ConnectionToCreate  = selectedTarget;
                                        selectedInstance.FlagLinkRuleApplied = true;
                                        if (step >= startStep)
                                        {
                                            if (recordTargetSelection)
                                            {
                                                if (TargetSelected != null)
                                                {
                                                    TargetSelected(selectedTarget.Instance, selectedTarget.Type, selectedRule);
                                                }
                                            }
                                        }

                                        //a structure rule can only be applied once per step so remove it
                                        selectedInstance.ApplicableRules.Remove(selectedRule);
                                    }
                                    else
                                    {
                                        isRuleApplicable = false;
                                    }
                                }
                            } break;

                            case RuleType.LINK_DESTRUCTION: {
                                LinkRule lr = selectedRule as LinkRule;
                                if (lr.Target is InstanceIdentifier)
                                {
                                    string       typeName   = (lr.Target as InstanceIdentifier).Value;
                                    IndexedMType targetType = indexedTypesByName[typeName];
                                    int          cCount     = selectedInstance.ConnectionCount(targetType);
                                    if (cCount > 0)
                                    {
                                        ActiveInstance selectedTarget = selectedInstance.GetTargetAtIndex(rand.Next(cCount), targetType);

                                        selectedInstance.Instance.Multiset.Subtract(lr.Lhs);
                                        ruleApplied(selectedRule, selectedInstance.Instance);
                                        linkRuleApplied = true;
                                        //selected target can't be null here
                                        selectedInstance.ConnectionToDestroy = selectedTarget;
                                        selectedInstance.FlagLinkRuleApplied = true;
                                        if (step >= startStep)
                                        {
                                            if (recordTargetSelection)
                                            {
                                                if (TargetSelected != null)
                                                {
                                                    TargetSelected(selectedTarget.Instance, selectedTarget.Type, selectedRule);
                                                }
                                            }
                                        }

                                        //a structure rule can only be applied once per step so remove it
                                        selectedInstance.ApplicableRules.Remove(selectedRule);
                                    }
                                    else
                                    {
                                        isRuleApplicable = false;
                                    }
                                }
                            } break;

                            case RuleType.MEMBRANE_DIVISION: {
                                DivisionRule dr = selectedRule as DivisionRule;
                                selectedInstance.Instance.Multiset.Subtract(dr.Lhs);
                                foreach (InstanceBlueprint ib in dr.Rhs)
                                {
                                    selectedInstance.AddInstanceBlueprint(ib, indexedTypesByName[ib.Type.Name]);
                                }
                                selectedInstance.FlagDivided = true;
                                ruleApplied(selectedRule, selectedInstance.Instance);
                                divisionRuleApplied = true;
                            } break;
                            }
                        }


                        if (selectedInstance.FlagDissolved || selectedInstance.FlagDivided)
                        {
                            allOperationalInstances.Remove(selectedInstance);
                            endStepForInstance = true;
                        }
                        else
                        {
                            switch (ex.Operator)
                            {
                            case StrategyOperator.SEQUENCE: {
                                if (isRuleApplicable)
                                {
                                    selectedInstance.ApplicableRules.Remove(selectedRule);
                                }
                                else
                                {
                                    endStepForInstance = true;
                                }
                            } break;

                            case StrategyOperator.MAX: {
                                if (!isRuleApplicable)
                                {
                                    selectedInstance.ApplicableRules.Remove(selectedRule);
                                }
                            } break;

                            case StrategyOperator.CHOICE: {
                                if (isRuleApplicable)
                                {
                                    advanceStrategyBlock = true;
                                }
                                else
                                {
                                    selectedInstance.ApplicableRules.Remove(selectedRule);
                                }
                            } break;

                            case StrategyOperator.ARBITRARY: {
                                if (!isRuleApplicable)
                                {
                                    if (selectedRule == null)
                                    {
                                        advanceStrategyBlock = true;
                                    }
                                    else
                                    {
                                        selectedInstance.ApplicableRules.Remove(selectedRule);
                                    }
                                }
                            } break;
                            }
                        }
                    }

                    if (endStepForInstance)
                    {
                        activeInstances.Remove(selectedInstance);
                    }
                    else
                    {
                        if (selectedInstance.ApplicableRules.Count == 0)
                        {
                            advanceStrategyBlock = true;
                        }

                        if (advanceStrategyBlock)
                        {
                            ex = ex.Next;

                            //if the next execution block is null, then remove this compartment from the active instance array
                            if (ex == null)
                            {
                                activeInstances.Remove(selectedInstance);
                            }
                            else
                            {
                                selectedInstance.CurrentStrategySegment = ex;
                            }
                        }
                    }

                    aiCount = activeInstances.Count;
                }

                if (rulesApplied == 0)
                {
                    isHalted = true;
                }
                else
                {
                    //Clear buffer for all instances;

                    foreach (ActiveInstance instance in allInstances)
                    {
                        instance.CommitBuffer();

                        if (linkRuleApplied)
                        {
                            if (instance.FlagLinkRuleApplied)
                            {
                                instance.CommitConnectionUpdates();
                            }
                        }
                    }

                    if (dissolutionRuleApplied || divisionRuleApplied)
                    {
                        foreach (ActiveInstance instance in allInstances)
                        {
                            if (instance.FlagDissolved)
                            {
                                instance.Instance.IsDissolved = true;
                                deadCells.Add(instance);
                                instance.CommitDissolution();
                            }
                            else if (instance.FlagDivided)
                            {
                                instance.Instance.IsDivided = true;
                                deadCells.Add(instance);
                                instance.CommitNewInstances(onNewInstanceCreated);
                            }
                        }

                        if (divisionRuleApplied)
                        {
                            foreach (ActiveInstance ai in newInstanceSet)
                            {
                                allInstances.Add(ai);
                            }
                            newInstanceSet.Clear();
                        }
                    }

                    foreach (ActiveInstance instance in deadCells)
                    {
                        //remove from allInstances collection such that a dead instance will never be
                        //considered for updates or any sort of operations
                        allInstances.Remove(instance);
                        //remove this instance from the set of instances associated to its type so
                        //it will never be considered for link creation or destruction
                        instance.IndexedMType.Instances.Remove(instance);
                    }

                    if (deadCells.Count > 0)
                    {
                        deadCells.Clear();
                    }

                    //reset execution strategy to begining
                    //it's important this is done after everthing has been commited, because the guards must be evaluated on the updated multiset
                    //in the instance
                    foreach (ActiveInstance ai in allOperationalInstances)
                    {
                        ai.ResetCurrentStrategySegment();
                    }

                    if (step >= startStep)
                    {
                        if (SimulationParams.RecordConfigurations)
                        {
                            if (StepComplete != null)
                            {
                                simStep.Step = step;
                                StepComplete(simStep);
                            }
                        }
                    }
                    ++step;
                }
            }

            --step;
            if (IsHalted() && SystemHalted != null)
            {
                SystemHalted(step);
            }
            if (SimulationComplete != null)
            {
                SimulationComplete(step);
            }

            return(kp);
        }