예제 #1
0
        public override bool Equals(object obj)
        {
            if (!(obj is Strand))
            {
                return(false);
            }
            Strand other = (Strand)obj;

            if (this.arguments.Count != other.arguments.Count)
            {
                return(false);
            }
            List <Node> myList    = this.arguments.ToList <Node>();
            List <Node> otherList = other.arguments.ToList <Node>();

            for (int i = 0; i < myList.Count; i++)
            {
                if (!myList[i].Equals(otherList[i]))
                {
                    return(false);
                }
            }

            return(true);
        }
예제 #2
0
        /// <summary>
        /// Builds a <see cref="Node"/> representing a <see cref="Strand"/> construction.
        /// </summary>
        /// <param name="nodes">The <see cref="Node"/>s to add to the <see cref="Strand"/>.</param>
        /// <returns>Returns a <see cref="Strand"/> containing the given <see cref="Node"/>s.</returns>
        public static Strand Strand(IEnumerable <Node> nodes)
        {
            Strand strand = new Strand();

            foreach (Node node in nodes)
            {
                strand.AddLast(node);
            }
            return(strand);
        }
예제 #3
0
        private static string ToDot(string parent, Strand node)
        {
            string name = String.Format("Strand{0}", counter++);

            foreach (Node argument in node.Items)
            {
                string itemName = ToDot(name, argument);
                text.AppendFormat("  {0} -> {1};\n", name, itemName);
            }
            return(name);
        }
예제 #4
0
        /// <summary>Generates a DLR Expression for Strand assignment.</summary>
        /// <remarks>
        ///  Transform this:
        /// (a;b;...) := .....    // don't care what is there :)
        /// 
        /// to this in DLR:
        /// 
        /// $__VALUES__ = (AType) .....; // ..... is a generated DLR expression now!
        /// 
        /// if($__VALUES__.IsArray)     // case A
        /// {
        ///     if($VALUES.length != 2)  // 2 the # of targets
        ///     {
        ///         throw new Error.Length("assign");
        ///     }
        ///     
        ///     a = disclose( ((AArray)$__VALUES__)[0] );
        ///     b = disclose( ((AArray)$__VALUES__)[1] );
        ///     ...
        /// }
        /// else    // case B
        /// {
        ///     // need to disclose the box
        ///     if($__VALUES__.Type == ATypes.Box)
        ///     {
        ///         $__VALUES__ = disclose($__VALUES__);
        ///     }
        ///     a = $VALUES.Clone();
        ///     b = $VALUES.Clone();
        ///     ...
        /// }
        /// $__DependencyManager__.InvalidateDependencies(string[] { a,b, .. })
        /// $__DependencyManager__.ValidateDependencies(string[] { a,b, .. })
        /// </remarks>
        /// <param name="scope"></param>
        /// <param name="targets">
        /// Strand containing Identifiers.
        /// If a node which in not an Identifier found, ParseException is thrown
        /// </param>
        /// <param name="value">The generated value which will be assigned to the targets</param>
        /// <returns>A generated DLR expression for strand assignment</returns>
        private static DLR.Expression GenerateStrandAssign(AplusScope scope, Strand targets, DLR.Expression value)
        {
            AbstractMonadicFunction disclose = MonadicFunctionInstance.Disclose;
            Aplus runtime = scope.GetRuntime();
            DLR.ParameterExpression environment = scope.GetRuntimeExpression();

            DLR.ParameterExpression valuesParam = DLR.Expression.Parameter(typeof(AType), "__VALUES__");
            // for dependency evaluation
            List<string> targetVariables = new List<string>();

            // for case A) assigns
            List<DLR.Expression> strand2StrandAssigns = new List<DLR.Expression>();
            // for case B) assigns
            List<DLR.Expression> strand2ValueAssigns = new List<DLR.Expression>()
            {
                DLR.Expression.Assign(
                    valuesParam,
                    DLR.Expression.Call(
                        DLR.Expression.Constant(disclose),
                        disclose.GetType().GetMethod("Execute"),
                        valuesParam,
                        environment
                    )
                )
            };

            int indexCounter = 0;

            foreach (Node node in targets.Items)
            {
                if (!(node is Identifier))
                {
                    throw new ParseException("assign lhs");
                }
                Identifier id = (Identifier)node;

                DLR.Expression strandValue =
                    DLR.Expression.Call(
                        DLR.Expression.Constant(disclose),
                        disclose.GetType().GetMethod("Execute"),
                        DLR.Expression.MakeIndex(
                            valuesParam,
                            typeof(AType).GetIndexerProperty(typeof(int)), // The indexer property which will be used
                            new DLR.Expression[] { DLR.Expression.Constant(indexCounter, typeof(int)) }
                        ),
                        environment
                );

                // case A) $TARGETS[i] = disclose($VALUES[i])
                strand2StrandAssigns.Add(GenerateIdentifierAssign(scope, id, strandValue, isStrand: true));

                // case B) $TARGETS[i] = $VALUE.Clone()
                strand2ValueAssigns.Add(
                    GenerateIdentifierAssign(
                        scope,
                        id,
                        DLR.Expression.Condition(
                            DLR.Expression.Property(valuesParam, "IsMemoryMappedFile"),
                            valuesParam,
                            DLR.Expression.Call(
                                valuesParam,
                                typeof(AType).GetMethod("Clone")
                            )
                        ),
                        isStrand: true
                    )
                );

                // gather the global variables for dependency validation/invalidation. 
                if ((scope.IsMethod && id.IsEnclosed) || !scope.IsMethod)
                {
                    targetVariables.Add(id.BuildQualifiedName(runtime.CurrentContext));
                }

                indexCounter++;
            }

            // case A)
            DLR.Expression caseStrand2Strand =
                DLR.Expression.IfThenElse(
                    DLR.Expression.NotEqual(
                        DLR.Expression.PropertyOrField(valuesParam, "Length"),
                        DLR.Expression.Constant(indexCounter, typeof(int))
                    ),
                    DLR.Expression.Throw(
                        DLR.Expression.New(
                            typeof(Error.Length).GetConstructor(new Type[] { typeof(string) }),
                            DLR.Expression.Constant("assign", typeof(string))
                        )
                    ),
                    DLR.Expression.Block(strand2StrandAssigns)
            );

            DLR.Expression dependencyManager = DLR.Expression.Property(scope.GetRuntimeExpression(), "DependencyManager");

            DLR.Expression result = DLR.Expression.Block(
                new DLR.ParameterExpression[] { valuesParam },
                DLR.Expression.Assign(valuesParam, DLR.Expression.Convert(value, typeof(AType))),
                DLR.Expression.IfThenElse(
                    DLR.Expression.PropertyOrField(valuesParam, "IsArray"),
                // case A)
                    caseStrand2Strand,
                // case B)
                    DLR.Expression.Block(strand2ValueAssigns)
                ),
                DLR.Expression.Call(
                    dependencyManager,
                    typeof(DependencyManager).GetMethod("InvalidateDependencies", new Type[] { typeof(string[]) }),
                    DLR.Expression.Constant(targetVariables.ToArray())
                ),
                DLR.Expression.Call(
                    dependencyManager,
                    typeof(DependencyManager).GetMethod("ValidateDependencies"),
                    DLR.Expression.Constant(targetVariables.ToArray())
                ),
                valuesParam
            );

            return DLR.Expression.Block(result, DLR.Expression.Assign(scope.CallbackInfo.NonPresetValue, value));
        }
예제 #5
0
 private static string ToDot(string parent, Strand node)
 {
     string name = String.Format("Strand{0}", counter++);
     foreach (Node argument in node.Items)
     {
         string itemName = ToDot(name, argument);
         text.AppendFormat("  {0} -> {1};\n", name, itemName);
     }
     return name;
 }
예제 #6
0
 /// <summary>
 /// Builds a <see cref="Node"/> representing a <see cref="Strand"/> construction.
 /// </summary>
 /// <param name="nodes">The <see cref="Node"/>s to add to the <see cref="Strand"/>.</param>
 /// <returns>Returns a <see cref="Strand"/> containing the given <see cref="Node"/>s.</returns>
 public static Strand Strand(IEnumerable<Node> nodes)
 {
     Strand strand = new Strand();
     foreach (Node node in nodes)
     {
         strand.AddLast(node);
     }
     return strand;
 }