示例#1
0
        /// <summary>
        /// Given a list of args (during a new instance call), parse out the first one as the class name,
        /// and convert the rest into an object array suitable for passing through reflection.
        /// </summary>
        private static (Type type, object[] varargs) ParseArgsForConstructorInterop(VarArgs args)
        {
            Cons list  = args.cons;
            Val  first = list?.first ?? Val.NIL;

            Type type = GetTypeFromNameOrObject(first);

            object[] varargs = TurnConsIntoBoxedArray(list?.rest);
            return(type, varargs);
        }
示例#2
0
        /// <summary>
        /// Parse out the first argument as a type based on name or instance,
        /// and the second as a member that's either a field or a property field.
        /// </summary>
        private static (Type type, string member) ParseArgsForMemberSearch(VarArgs args)
        {
            Cons list   = args.cons;
            Val  first  = list?.first ?? Val.NIL;
            Val  second = list?.second ?? Val.NIL;

            Type   type   = GetTypeFromNameOrObject(first);
            string member = GetStringOrSymbolName(second);

            return(type, member);
        }
示例#3
0
        ///// <summary> Performs a right fold on the array: +, 0, [1, 2, 3] => (1 + (2 + (3 + 0))) </summary>
        private static Val FoldRight(Func <Val, Val, Val> fn, Val baseElement, VarArgs args)
        {
            var result   = baseElement;
            var elements = args.ToNativeList();

            for (int i = elements.Count - 1; i >= 0; i--)
            {
                result = fn(elements[i], result);
            }
            return(result);
        }
示例#4
0
        ///// <summary> Performs a left fold on the array: +, 0, [1, 2, 3] => (((0 + 1) + 2) + 3) </summary>
        private static Val FoldLeft(Func <Val, Val, Val> fn, Val baseElement, VarArgs args)
        {
            var result   = baseElement;
            var elements = args.ToNativeList();

            for (int i = 0, len = elements.Count; i < len; i++)
            {
                result = fn(result, elements[i]);
            }
            return(result);
        }
示例#5
0
        //
        //
        // dotnet interop

        public static Val DotDot(Context _, VarArgs args)
        {
            var arglist = args.ToNativeList().SelectMany(SplitSymbol).ToList();

            var gotone = arglist.Count > 0;

            if (!gotone)
            {
                return(Val.NIL);
            }

            int i       = 0;
            var current = arglist[i++];

            do
            {
                var nextSymbol = TakeNextSymbolOrNull();
                var nonSymbols = TakeNonSymbols().ToList();
                current = TryReflectionStep(current, nextSymbol, nonSymbols);
            } while (i < arglist.Count);

            return(current);

            Symbol TakeNextSymbolOrNull()
            {
                var results = TakeSymbols(true).Take(1);

                return(results.FirstOrDefault().AsSymbolOrNull);
            }

            IEnumerable <Val> TakeNonSymbols()
            {
                return(TakeSymbols(false));
            }

            IEnumerable <Val> TakeSymbols(bool expected)
            {
                while (i < arglist.Count)
                {
                    var next = arglist[i];
                    if (next.IsSymbol == expected)
                    {
                        i++;
                        yield return(next);
                    }
                    else
                    {
                        break;
                    }
                }
            }
        }
示例#6
0
        /// <summary>
        /// Given an instance as the first argument, parse out its type,
        /// and parse the second arg as a member that's either a field or a property field.
        /// If the setter flag is set, it also parses out the third element as the new value.
        /// </summary>
        private static (object instance, Type type, string member, Val third, Val fourth) ParseSetterArgs(VarArgs args, bool setter)
        {
            Cons list   = args.cons;
            Val  first  = list?.first ?? Val.NIL;
            Val  second = list?.second ?? Val.NIL;
            Val  third  = (setter && list != null) ? list.third : Val.NIL;
            Val  fourth = (setter && list != null && list.afterThird.IsNotNil) ? list.fourth : Val.NIL;

            var    instance = first.AsBoxedValue;
            Type   type     = instance?.GetType();
            string member   = GetStringOrSymbolName(second);

            return(instance, type, member, third, fourth);
        }
示例#7
0
        /// <summary>
        /// Given a list of args (for a function call), parse out the first one as the type we're referring to,
        /// second as method name, and convert the rest into an object array suitable for passing through reflection.
        /// </summary>
        private static (MethodInfo method, object instance, object[] varargs) ParseArgsForMethodCall(VarArgs args)
        {
            Cons list   = args.cons;
            Val  first  = list?.first ?? Val.NIL;
            Val  second = list?.second ?? Val.NIL;

            object     instance = first.AsObjectOrNull;
            MethodInfo method   = second.GetObjectOrNull <MethodInfo>();

            object[] varargs = TurnConsIntoBoxedArray(list?.afterSecond);
            return(method, instance, varargs);
        }
示例#8
0
        /// <summary>
        /// Given a list of args (during a method search), parse out the first one as the name class,
        /// second as method name, and convert the rest into an object array suitable for passing through reflection.
        /// </summary>
        private static (Type type, string member, object[] varargs) ParseArgsForMethodSearch(VarArgs args)
        {
            Cons list   = args.cons;
            Val  first  = list?.first ?? Val.NIL;
            Val  second = list?.second ?? Val.NIL;

            Type   type   = GetTypeFromNameOrObject(first);
            string member = GetStringOrSymbolName(second);

            object[] varargs = TurnConsIntoBoxedArray(list?.afterSecond);
            return(type, member, varargs);
        }
示例#9
0
        /// <summary>
        /// Given an instance as the first argument, parse out its type,
        /// and parse the second arg as a member that's either a field or a property field.
        /// If the setter flag is set, it also parses out the third element as the new value.
        /// </summary>
        private static (object instance, Type type, string member, Val third) ParseMemberFromInstance(VarArgs args, bool setter)
        {
            Cons list   = args.cons;
            Val  first  = list?.first ?? Val.NIL;
            Val  second = list?.second ?? Val.NIL;
            Val  third  = (setter && list != null) ? list.third : Val.NIL;

            var    instance = first.AsBoxedValue;
            Type   type     = instance?.GetType();
            string member   = GetStringOrSymbolName(second);

            return(instance, type, member, third);
        }