/// <summary> /// 行ないし括弧の中身にドット構文があればDotBlockに置換する /// </summary> /// <param name="block"></param> /// <returns></returns> static object[] GroupToDotBlock(IEnumerable<object> block) { foreach (object t in block) { if (t is PareBlock)//引数などに存在しうるドット構文を先に処理 { var p = t as PareBlock; p.tokens = GroupToDotBlock(p.tokens); } if (t is OptionBlock) { var o = t as OptionBlock; o.Tokens = GroupToDotBlock(o.Tokens); } } var src = new LinkedList<object>(block); LinkedListNode<object> current = src.First; while (current != null) { if (current.Value is Marks && ((Marks)current.Value) == Marks.Dot) { var dot = new DotBlock(current.Previous.Value, current.Next.Value); src.Remove(current.Previous); src.Remove(current.Next); src.AddAfter(current, dot); current = current.Next; src.Remove(current.Previous);//ドット前後3トークンを削除してDotBlockに置き換え } else { current = current.Next; } } return src.ToArray(); }
Expression ProcessDotBlock(DotBlock dot) { Type leftType; Expression left; ClassReflectionInfo info; var id = dot.Left as string; if (id != null && TypeNameDictionary.ContainsKey(id))//静的メンバアクセス { left = null; leftType = TypeNameDictionary[id]; } else { left = ProcessSingleToken(dot.Left); leftType = left.Type; } info = GetObjectInfo(leftType); string op; object[] args; if (dot.Right is string) { op = dot.Right as string; args = null; } else if (dot.Right is PareBlock) { var pare = dot.Right as PareBlock; op = pare.tokens[0] as string; args = pare.tokens.Skip(1).ToArray(); } else { throw new ParseException("ドット演算子の右に不正なトークン:" + dot.ToString()); } if (left != null) { var pf = TryGetPropertyOrField(op, left); if (pf != null) { return pf; } var res = TryCallInstanceMethod(op, args, left); if (res != null) { return res; } } else { if (info.StaticMethodDict.ContainsKey(op)) { return CallExternalMethodInner(info.StaticMethodDict[op], args, null); } else if (op == "new") { return CallConstructor(leftType, args); } else { var res = CallStaticNonScriptMethod(leftType, op, args); if (res != null) { return res; } } } throw new ParseException("ドット演算子右辺の識別子が不明:" + dot.ToString()); }