public void AddAnonymousType (AnonymousTypeClass type) { ArrayList existing = (ArrayList)anonymous_types [type.Parameters.Count]; if (existing == null) { existing = new ArrayList (); anonymous_types.Add (type.Parameters.Count, existing); } existing.Add (type); }
public void AddAnonymousType (AnonymousTypeClass type) { List<AnonymousTypeClass> existing; if (!anonymous_types.TryGetValue (type.Parameters.Count, out existing)) if (existing == null) { existing = new List<AnonymousTypeClass> (); anonymous_types.Add (type.Parameters.Count, existing); } existing.Add (type); }
public static AnonymousTypeClass Create (TypeContainer parent, IList<AnonymousTypeParameter> parameters, Location loc) { string name = ClassNamePrefix + parent.Module.CounterAnonymousTypes++; ParametersCompiled all_parameters; TypeParameters tparams = null; SimpleName[] t_args; if (parameters.Count == 0) { all_parameters = ParametersCompiled.EmptyReadOnlyParameters; t_args = null; } else { t_args = new SimpleName[parameters.Count]; tparams = new TypeParameters (); Parameter[] ctor_params = new Parameter[parameters.Count]; for (int i = 0; i < parameters.Count; ++i) { AnonymousTypeParameter p = parameters[i]; for (int ii = 0; ii < i; ++ii) { if (parameters[ii].Name == p.Name) { parent.Compiler.Report.Error (833, parameters[ii].Location, "`{0}': An anonymous type cannot have multiple properties with the same name", p.Name); p = new AnonymousTypeParameter (null, "$" + i.ToString (), p.Location); parameters[i] = p; break; } } t_args[i] = new SimpleName ("<" + p.Name + ">__T", p.Location); tparams.Add (new TypeParameter (i, new MemberName (t_args[i].Name, p.Location), null, null, Variance.None)); ctor_params[i] = new Parameter (t_args[i], p.Name, Parameter.Modifier.NONE, null, p.Location); } all_parameters = new ParametersCompiled (ctor_params); } // // Create generic anonymous type host with generic arguments // named upon properties names // AnonymousTypeClass a_type = new AnonymousTypeClass (parent.Module, new MemberName (name, tparams, loc), parameters, loc); Constructor c = new Constructor (a_type, name, Modifiers.PUBLIC | Modifiers.DEBUGGER_HIDDEN, null, all_parameters, loc); c.Block = new ToplevelBlock (parent.Module.Compiler, c.ParameterInfo, loc); // // Create fields and constructor body with field initialization // bool error = false; for (int i = 0; i < parameters.Count; ++i) { AnonymousTypeParameter p = parameters [i]; Field f = new Field (a_type, t_args [i], Modifiers.PRIVATE | Modifiers.READONLY | Modifiers.DEBUGGER_HIDDEN, new MemberName ("<" + p.Name + ">", p.Location), null); if (!a_type.AddField (f)) { error = true; continue; } c.Block.AddStatement (new StatementExpression ( new SimpleAssign (new MemberAccess (new This (p.Location), f.Name), c.Block.GetParameterReference (i, p.Location)))); ToplevelBlock get_block = new ToplevelBlock (parent.Module.Compiler, p.Location); get_block.AddStatement (new Return ( new MemberAccess (new This (p.Location), f.Name), p.Location)); Property prop = new Property (a_type, t_args [i], Modifiers.PUBLIC, new MemberName (p.Name, p.Location), null); prop.Get = new Property.GetMethod (prop, 0, null, p.Location); prop.Get.Block = get_block; a_type.AddMember (prop); } if (error) return null; a_type.AddConstructor (c); return a_type; }
public static AnonymousTypeClass Create (CompilerContext ctx, TypeContainer parent, IList<AnonymousTypeParameter> parameters, Location loc) { string name = ClassNamePrefix + types_counter++; SimpleName [] t_args = new SimpleName [parameters.Count]; TypeParameterName [] t_params = new TypeParameterName [parameters.Count]; Parameter [] ctor_params = new Parameter [parameters.Count]; for (int i = 0; i < parameters.Count; ++i) { AnonymousTypeParameter p = (AnonymousTypeParameter) parameters [i]; t_args [i] = new SimpleName ("<" + p.Name + ">__T", p.Location); t_params [i] = new TypeParameterName (t_args [i].Name, null, p.Location); ctor_params [i] = new Parameter (t_args [i], p.Name, 0, null, p.Location); } // // Create generic anonymous type host with generic arguments // named upon properties names // AnonymousTypeClass a_type = new AnonymousTypeClass (parent.NamespaceEntry.SlaveDeclSpace, new MemberName (name, new TypeArguments (t_params), loc), parameters, loc); if (parameters.Count > 0) a_type.SetParameterInfo (null); Constructor c = new Constructor (a_type, name, Modifiers.PUBLIC | Modifiers.DEBUGGER_HIDDEN, null, new AnonymousParameters (ctx, ctor_params), null, loc); c.Block = new ToplevelBlock (ctx, c.ParameterInfo, loc); // // Create fields and contructor body with field initialization // bool error = false; for (int i = 0; i < parameters.Count; ++i) { AnonymousTypeParameter p = (AnonymousTypeParameter) parameters [i]; Field f = new Field (a_type, t_args [i], Modifiers.PRIVATE | Modifiers.READONLY, new MemberName ("<" + p.Name + ">", p.Location), null); if (!a_type.AddField (f)) { error = true; continue; } c.Block.AddStatement (new StatementExpression ( new SimpleAssign (new MemberAccess (new This (p.Location), f.Name), c.Block.GetParameterReference (p.Name, p.Location)))); ToplevelBlock get_block = new ToplevelBlock (ctx, p.Location); get_block.AddStatement (new Return ( new MemberAccess (new This (p.Location), f.Name), p.Location)); Property prop = new Property (a_type, t_args [i], Modifiers.PUBLIC, new MemberName (p.Name, p.Location), null); prop.Get = new Property.GetMethod (prop, 0, null, p.Location); prop.Get.Block = get_block; a_type.AddProperty (prop); } if (error) return null; a_type.AddConstructor (c); return a_type; }
public override Expression DoResolve (ResolveContext ec) { if (ec.HasSet (ResolveContext.Options.ConstantScope)) { ec.Report.Error (836, loc, "Anonymous types cannot be used in this expression"); return null; } if (parameters == null) { anonymous_type = CreateAnonymousType (ec, EmptyParameters); RequestedType = new TypeExpression (anonymous_type.TypeBuilder, loc); return base.DoResolve (ec); } bool error = false; Arguments = new Arguments (parameters.Count); TypeExpression [] t_args = new TypeExpression [parameters.Count]; for (int i = 0; i < parameters.Count; ++i) { Expression e = ((AnonymousTypeParameter) parameters [i]).Resolve (ec); if (e == null) { error = true; continue; } Arguments.Add (new Argument (e)); t_args [i] = new TypeExpression (e.Type, e.Location); } if (error) return null; anonymous_type = CreateAnonymousType (ec, parameters); if (anonymous_type == null) return null; RequestedType = new GenericTypeExpr (anonymous_type.TypeBuilder, new TypeArguments (t_args), loc); return base.DoResolve (ec); }