internal static void addCaseLineToCurrentCopyCommVar(Variable orjVariable, Variable copyCommVar, KpCore.Rule rule, Module module, Module targetModule, int strategyIndex) { //for each variable generate a case line CaseLine caseLine = new CaseLine(); OperExp result = new OperExp(); int resultValue = 0; RewriteCommunicationRule rcr = (RewriteCommunicationRule)rule; foreach (var target in rcr.TargetRhs.Values) { TargetedMultiset targetMultiSet = (TargetedMultiset)target; InstanceIdentifier targetType = (InstanceIdentifier)targetMultiSet.Target; if (targetModule.Type == targetType.Value) { Multiset ms = targetMultiSet.Multiset; foreach (var obj in ms.Objects) { if (obj.Equals(orjVariable.Name)) { resultValue += ms[obj]; } } } } result.Exp = copyCommVar.Name; if (resultValue != 0) { result.Oper.Value = MathOper.ADD; result.Result = new Expression(resultValue.ToString()); } caseLine.Result = result; caseLine.Rule = BRulesStandardVar.extractStandardRuleFromKPRule(rule, module, strategyIndex); ICondition sequenceCondition = BRulesStandardVar.getSequenceCondition(module, strategyIndex, rule.Id); ICondition targetBounds = getBoundCondition(copyCommVar, caseLine.Result); CompoundBoolExpression sequenceAndBound = new CompoundBoolExpression(sequenceCondition, BinaryOperator.AND, targetBounds); ICondition statusCondition = BRulesStandardVar.getTurnCondition(module, strategyIndex); CompoundBoolExpression statusAndSequence = new CompoundBoolExpression(statusCondition, BinaryOperator.AND, sequenceAndBound); // _conn = to_c2 if (module.connectionToModuleExist(targetModule)) { BoolExp connEqInstance = new BoolExp(module.getConnectionToModule(targetModule).Name, NuSMV.RelationalOperator.EQUAL, SMVPreFix.getConnectedTo(targetModule.Instance)); caseLine.Rule.AddBoolExpression(connEqInstance, BinaryOperator.AND); } caseLine.Rule.AddBoolExpression(statusAndSequence, BinaryOperator.AND); caseLine.Rule.ID = rule.Id; if (copyCommVar.Next != null) { //if the case line has not added yet if (!ruleExist(copyCommVar.Next, caseLine)) { copyCommVar.Next.addCaseLine(caseLine); } } }
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); }
/// <summary> /// if current type, has communication rules which sends to target type /// </summary> /// <param name="currentType">current KP type</param> /// <param name="targetType">target KP Type</param> /// <returns></returns> private static bool communicationRuleIncludesTargetType(MType currentType, MType targetType) { bool communicationRuleToTargetExist = false; ExecutionStrategy kpEs = currentType.ExecutionStrategy; while (kpEs != null) { foreach (var rule in kpEs.Rules) { if (rule.Type == RuleType.REWRITE_COMMUNICATION) { RewriteCommunicationRule rcr = (RewriteCommunicationRule)rule; foreach (var target in rcr.TargetRhs.Values) { TargetedMultiset targetMultiSet = (TargetedMultiset)target; InstanceIdentifier targetTypeIdent = (InstanceIdentifier)targetMultiSet.Target; if (targetType.Name == targetTypeIdent.Value) { communicationRuleToTargetExist = true; break; } } } if (communicationRuleToTargetExist) { break; } } if (communicationRuleToTargetExist) { break; } kpEs = kpEs.Next; } return(communicationRuleToTargetExist); }
private void Build() { a = new Alphabet(); allInstances = new HashSet <MInstance>(); instanceTypes = new Dictionary <MInstance, MType>(); idMap = new KpIdMap(kp); growthPerType = new int[kp.Types.Count]; foreach (MType mtype in kp.Types) { foreach (MInstance instance in mtype.Instances) { registerSymbols(instance.Multiset); allInstances.Add(instance); instanceTypes.Add(instance, mtype); } ExecutionStrategy ex = mtype.ExecutionStrategy; while (ex != null) { foreach (Rule r in ex.Rules) { if (r is ConsumerRule) { registerSymbols((r as ConsumerRule).Lhs); if (r.Type == RuleType.MULTISET_REWRITING) { registerSymbols((r as RewritingRule).Rhs); } else if (r.Type == RuleType.REWRITE_COMMUNICATION) { RewriteCommunicationRule rcr = r as RewriteCommunicationRule; registerSymbols(rcr.Rhs); foreach (TargetedMultiset tm in rcr.TargetRhs.Values) { registerSymbols(tm.Multiset); } HasCommunication = true; } else if (r.Type == RuleType.LINK_CREATION) { HasLinkCreation = true; } else if (r.Type == RuleType.LINK_DESTRUCTION) { HasLinkDestruction = true; } else if (r.Type == RuleType.MEMBRANE_DIVISION) { HasDivision = true; foreach (InstanceBlueprint ib in (r as DivisionRule).Rhs) { registerSymbols(ib.Multiset); growthPerType[ib.Type.Id]++; } } else if (r.Type == RuleType.MEMBRANE_DISSOLUTION) { HasDissolution = true; } if (r.IsGuarded) { registerSymbols(r.Guard); } } } ex = ex.Next; } } }
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()); }
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(); }
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); }
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(); }
/// <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); }
private static void buildCommunicationVariables(SMVModel nuSMV, NuSMV.Module module, KPsystem kpSystem, KpCore.MType type, int strategyIndex, KpCore.Rule rule) { RewriteCommunicationRule rcr = (RewriteCommunicationRule)rule; string varName = ""; VariableOrigin origin = VariableOrigin.Original; bool isLeft = true; //regular left hand-side rules foreach (var leftHRule in rcr.Lhs) { varName = leftHRule.Key; isLeft = true; buildReWritingVariable(kpSystem, type, module, strategyIndex, rule, varName, origin, isLeft); } //regular right hand-side rules foreach (var rigthHRule in rcr.Rhs) { varName = rigthHRule.Key; origin = VariableOrigin.Original; isLeft = false; //first generate original one, then its copy if (!module.isVariableExist(varName)) { buildReWritingVariable(kpSystem, type, module, strategyIndex, rule, varName, origin, isLeft); } string copyVarName = varName + SMVPreFix.COPY; origin = VariableOrigin.Copy; buildReWritingVariable(kpSystem, type, module, strategyIndex, rule, copyVarName, origin, isLeft); } //Targeted rules foreach (var target in rcr.TargetRhs.Values) { TargetedMultiset targetMultiSet = (TargetedMultiset)target; InstanceIdentifier targetTypeIdentifier = (InstanceIdentifier)targetMultiSet.Target; MType targetType = null; foreach (var tempType in kpSystem.Types) { if (tempType.Name == targetTypeIdentifier.Value) { targetType = tempType; } } //for each connected instance of the target type, create a copy variable foreach object in the multiset foreach (var connectedInstance in module.Instance.ConnectedTo) { if (connectedInstance.Module.Type == targetType.Name) { Module targetModule = connectedInstance.Module; Multiset ms = targetMultiSet.Multiset; foreach (var obj in ms.Objects) { varName = obj; Variable targetVariable = new Variable(varName); string currentCpVarName = SMVPreFix.getConnectedCopyCommVarName(varName, targetModule); Variable currentCpVar = new Variable(currentCpVarName); //create original variable inside target module if (!targetModule.isVariableExist(varName)) { setBoundIntType(kpSystem, targetType, targetModule, targetVariable); targetVariable.Behaviour = VariableBehaviour.COMMUNICATION; targetVariable.Origin = VariableOrigin.OriginalCommVar; targetVariable.Init = setOrUpdateInit(targetModule, targetVariable); targetModule.Variables.Add(targetVariable); } else { //if variable is already in target module, then make sure, it is set as communication var. targetVariable = (Variable)targetModule.Variables.First(item => item.Name.Equals(varName)); targetVariable.Behaviour = VariableBehaviour.COMMUNICATION; targetVariable.Origin = VariableOrigin.OriginalCommVar; targetVariable.Init = setOrUpdateInit(targetModule, targetVariable); } //create a varName_InstanceName_TargetModule, variable (as copy) inside current module. if (!module.isVariableExist(currentCpVarName)) { Variable orginalVariable = (Variable)targetModule.getVariable(varName); currentCpVar.Type = orginalVariable.Type; currentCpVar.Behaviour = VariableBehaviour.REWRITING; currentCpVar.Origin = VariableOrigin.CopyOfCommVar; currentCpVar.Init = "0"; module.Variables.Add(currentCpVar); } else { //if variable exists then update the values. currentCpVar = (Variable)module.Variables.First(item => item.Name.Equals(currentCpVarName)); } //add result of rule to caseline BRulesComVar.addCaseLineToCurrentCopyCommVar(targetVariable, currentCpVar, rule, module, targetModule, strategyIndex); } } } } }
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); }