public ICleanerNode Sub(ICleanerNode a) { if (typeof(ComplexCleanerNode) == a.GetType()) { ((ComplexCleanerNode)a).IterateOverComputables((IComputableCleanerNode node, int i) => { Sub(node); }); return(this); } else if (typeof(CleanerNode) == a.GetType()) { for (int i = 0; i < subNodes.Count; i++) { if (!typeof(IComputableCleanerNode).IsAssignableFrom(subNodes[i].GetType())) { continue; } IComputableCleanerNode node = (IComputableCleanerNode)subNodes[i]; if (CleanerNode.CanAdd((CleanerNode)node, (CleanerNode)a)) { subNodes[i] = (CleanerNode)node - (CleanerNode)a; } } return(this); } throw new System.NotImplementedException(); }
public static string Clean(string exp) { Queue <ICleanerNode> q = Shant(exp); Stack <ICleanerNode> s = new Stack <ICleanerNode>(); while (q.Count > 0) { ICleanerNode node = q.Dequeue(); if (node.GetType() == typeof(CleanerOperatorNode)) { CleanerOperatorNode operatorNode = (CleanerOperatorNode)node; IComputableCleanerNode n1 = s.Count > 0 ? (IComputableCleanerNode)s.Pop() : null; IComputableCleanerNode n2 = s.Count > 0 ? (IComputableCleanerNode)s.Pop() : null; ICleanerNode n = operatorNode.Execute(n2, n1); s.Push(n); } else { s.Push(node); } } return(s.Pop().ToString()); }
public ICleanerNode Execute(IComputableCleanerNode a, IComputableCleanerNode b) { switch (type) { case '+': if (a == null) { return(b); } return(a.Add(b)); case '-': if (a == null) { return(b.Multiply(new CleanerNode(-1, NO_ID))); } return(a.Sub(b)); case '*': return(a.Multiply(b)); case '/': return(a.Divide(b)); case '^': return(a.Power(b)); } throw new Exception(string.Format("Unsupported operation {0}", type)); }
public ICleanerNode Power(ICleanerNode a) { if (!typeof(IComputableCleanerNode).IsAssignableFrom(a.GetType())) { throw new System.Exception("Uncomputable node type " + a.GetType().Name); } powerNode = (IComputableCleanerNode)a; return(this); }
public ICleanerNode Add(ICleanerNode a) { if (typeof(ComplexCleanerNode) == a.GetType()) { ComplexCleanerNode ccna = ((ComplexCleanerNode)a); for (int j = 0; j < ccna.subNodes.Count; j++) { if (!typeof(IComputableCleanerNode).IsAssignableFrom(ccna.subNodes[j].GetType())) { continue; } Add(ccna.subNodes[j]); } return(this); } else if (typeof(CleanerNode) == a.GetType()) { bool added = false; for (int i = 0; i < subNodes.Count; i++) { if (!typeof(IComputableCleanerNode).IsAssignableFrom(subNodes[i].GetType())) { continue; } IComputableCleanerNode node = (IComputableCleanerNode)subNodes[i]; if (CleanerNode.CanAdd((CleanerNode)node, (CleanerNode)a)) { added = true; subNodes[i] = (CleanerNode)node + (CleanerNode)a; break; } } if (!added) { subNodes.Add(new CleanerOperatorNode('+')); subNodes.Add(a); } return(this); } throw new System.NotImplementedException(); }
public ICleanerNode Divide(ICleanerNode a) { if (a.GetType() == typeof(ComplexCleanerNode)) { if (a.IsEqual(this)) { return(new CleanerNode(1, CleanerOperatorNode.NO_ID)); } ComplexCleanerNode ccna = (ComplexCleanerNode)a; if (BodyEquals(ccna)) { ComplexCleanerNode n = new ComplexCleanerNode(subNodes.ToArray()); IComputableCleanerNode cpn = powerNode == null ? new CleanerNode(1, CleanerOperatorNode.NO_ID) : powerNode; IComputableCleanerNode apn = powerNode == null ? new CleanerNode(1, CleanerOperatorNode.NO_ID) : ccna.powerNode; n.powerNode = (IComputableCleanerNode)cpn.Sub(apn); return(n); } } return(new ComplexCleanerNode(this, new CleanerOperatorNode('/'), a)); }
public ComplexCleanerNode(params ICleanerNode[] nodes) { powerNode = null; subNodes = nodes.ToList(); }
public ICleanerNode Multiply(ICleanerNode a) { if (typeof(ComplexCleanerNode) == a.GetType()) { ComplexCleanerNode cnna = (ComplexCleanerNode)a; if (cnna.IsEqual(this)) { ComplexCleanerNode n = new ComplexCleanerNode(subNodes.ToArray()); if (cnna.powerNode == null && powerNode == null) { n.powerNode = new CleanerNode(2, CleanerOperatorNode.NO_ID); } else if (cnna.powerNode == null) { n.powerNode = (IComputableCleanerNode)powerNode.Add(new CleanerNode(1, CleanerOperatorNode.NO_ID)); } else if (powerNode == null) { n.powerNode = (IComputableCleanerNode)cnna.powerNode.Add(new CleanerNode(1, CleanerOperatorNode.NO_ID)); } else { n.powerNode = (IComputableCleanerNode)powerNode.Add(cnna.powerNode); } return(n); } if ((powerNode == null && cnna.powerNode == null) || (powerNode != null && !powerNode.IsEqual(cnna.powerNode)) || (powerNode == null && cnna.powerNode != null)) { return(new ComplexCleanerNode(this, new CleanerOperatorNode('*'), cnna)); } cnna.IterateOverComputables((IComputableCleanerNode node, int i) => { Multiply(node); }); return(this); } else if (typeof(CleanerNode) == a.GetType()) { if (powerNode != null) { return(new ComplexCleanerNode(this, new CleanerOperatorNode('*'), a)); } if (subNodes[1].GetType() == typeof(CleanerOperatorNode)) { if (((CleanerOperatorNode)subNodes[1]).type == '*' || ((CleanerOperatorNode)subNodes[1]).type == '/') { for (int i = 0; i < subNodes.Count; i++) { if (!typeof(IComputableCleanerNode).IsAssignableFrom(subNodes[i].GetType())) { continue; } IComputableCleanerNode node = (IComputableCleanerNode)subNodes[i]; subNodes[i] = node.Multiply((CleanerNode)a); break; } } else { for (int i = 0; i < subNodes.Count; i++) { if (!typeof(IComputableCleanerNode).IsAssignableFrom(subNodes[i].GetType())) { continue; } IComputableCleanerNode node = (IComputableCleanerNode)subNodes[i]; subNodes[i] = node.Multiply((CleanerNode)a); } } } return(this); } throw new System.NotImplementedException(); }