public virtual Type parameterize(Map pars) { if (this == Sys.ListType) { Type v = (Type)pars.get(FanStr.m_ascii['V']); if (v == null) { throw ArgErr.make("List.parameterize - V undefined").val; } return(v.toListOf()); } if (this == Sys.MapType) { Type v = (Type)pars.get(FanStr.m_ascii['V']); Type k = (Type)pars.get(FanStr.m_ascii['K']); if (v == null) { throw ArgErr.make("Map.parameterize - V undefined").val; } if (k == null) { throw ArgErr.make("Map.parameterize - K undefined").val; } return(new MapType(k, v)); } if (this == Sys.FuncType) { Type r = (Type)pars.get(FanStr.m_ascii['R']); if (r == null) { throw ArgErr.make("Map.parameterize - R undefined").val; } ArrayList p = new ArrayList(); for (int i = 'A'; i <= 'H'; ++i) { Type x = (Type)pars.get(FanStr.m_ascii[i]); if (x == null) { break; } p.Add(x); } return(new FuncType((Type[])p.ToArray(System.Type.GetType("Fan.Sys.Type")), r)); } throw UnsupportedErr.make("not generic: " + this).val; }
////////////////////////////////////////////////////////////////////////// // Collection ////////////////////////////////////////////////////////////////////////// /// <summary> /// collection := list | map /// </summary> private object readCollection(Field curField, Type t) { // opening [ consume(Token.LBRACKET, "Expecting '['"); // if this could be a map type signature: // [qname:qname] // [qname:qname][] // [qname:qname][][] ... // or it could just be the type signature of // of a embedded simple, complex, or list Type peekType = null; if (curt == Token.ID && t == null) { // peek at the type peekType = readType(); // if we have [mapType] then this is non-inferred type signature if (curt == Token.RBRACKET && peekType is MapType) { t = peekType; peekType = null; consume(); while (curt == Token.LRBRACKET) { consume(); t = t.toListOf(); } if (curt == Token.QUESTION) { consume(); t = t.toNullable(); } if (curt == Token.POUND) { consume(); return t; } consume(Token.LBRACKET, "Expecting '['"); } } // handle special case of [,] if (curt == Token.COMMA && peekType == null) { consume(); consume(Token.RBRACKET, "Expecting ']'"); return new List(toListOfType(t, curField, false)); } // handle special case of [:] if (curt == Token.COLON && peekType == null) { consume(); consume(Token.RBRACKET, "Expecting ']'"); return new Map(toMapType(t, curField, false)); } // read first list item or first map key object first = readObj(null, peekType, false); // now we can distinguish b/w list and map if (curt == Token.COLON) return readMap(toMapType(t, curField, true), first); else return readList(toListOfType(t, curField, true), first); }