public static IArgument Executable(CharSource source, ref char chr, Dictionary <string, IFunction> funcs) { // Having seen '<' if (!source.AdvanceWhiteSpace(out chr)) { throw new FinalCharacterException("Expected statements, or closing '>'"); } var exec = new ExecutableArgument(); // Statement reading takes us to the first character of the next potential while (true) { if (chr == '>') { source.Advance(out chr); return(exec); } var statement = Statement(source, ref chr, funcs); exec.Value.Add(statement); } }
public static IArgument Default(CharSource source, ref char chr) { if (CharSource.IsNameStart(chr)) { var name = source.ReadName(ref chr); if (bool.TryParse(name, out var bval)) { return(new BooleanLiteral() { Value = bval }); } return(new NameArgument() { Value = name }); } else if (CharSource.IsNumberStart(chr)) { return(Number(source, ref chr)); } throw new InvalidCharacterException($"Not a valid name or number start: '{chr}'"); }
public static ArgumentList Multiple(CharSource source, ref char chr, Dictionary <string, IFunction> funcs) { var args = new ArgumentList(); // Typically get here having seen nothing or the first character already // Running out of text here is not an error, unless specified as more to come while (source.SkipWhiteSpace(ref chr)) { var arg = Single(source, ref chr, funcs); args.Add(arg); if (!source.SkipWhiteSpace(ref chr)) { return(args); } else if (chr != ',') { return(args); } source.Advance(out chr); } // No need to throw here, as if more expected single argument parsing will catch return(args); }