//怎么取得匿名类型的Type放到//泛型T当中??var 匿名 = new { A = 0, B = 1 };Type t = 匿名.GetType();//然后下面var xx = dbContext.Database.SqlQuery("sql");//就悲剧了var xx2 = dbContext.Database.SqlQuery ("sql");//xx2有列表,但是都是Object..~~~无法显示真实项,用Profile跟..SQL确实提交了.求解释
msdn大神的
看到了所以记录下来
出现那个问题的原因是动态类型上没有 Entity Framework 需要的属性定义,Entity Framework 是通过反射类型上的属性来做映射的。为了解决这个问题,我用到了 Emit 技术,动态产生一个类型,并且动态写入 IL 代码产生属性。代码如下,测试在 C# 4.0 上通过。
using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Data.Entity;using System.Collections;using System.Reflection.Emit;using System.Reflection; namespace Demo{ public class Program { public static void Main(string[] args) { string connectionString = "Server=(local); Integrated Security=true; Database=master"; using (DbContext context = new DbContext(connectionString)) { TypeBuilder builder = Program.CreateTypeBuilder("MyDynamicAssembly", "MyModule", "MyType"); Program.CreateAutoImplementedProperty(builder, "name", typeof(string)); Program.CreateAutoImplementedProperty(builder, "type", typeof(string)); Program.CreateAutoImplementedProperty(builder, "id", typeof(int)); Type resultType = builder.CreateType(); dynamic queryResult = context.Database.SqlQuery(resultType, "SELECT * FROM sys.sysobjects"); Console.WriteLine("{0,20} {1,4} {2,10}", "Name", "Type", "ID"); foreach (dynamic item in queryResult) { Console.WriteLine("{0,10} {1,4} {2,10}", item.name, item.type, item.id); } } Console.ReadKey(); } public static TypeBuilder CreateTypeBuilder(string assemblyName, string moduleName, string typeName) { TypeBuilder typeBuilder = AppDomain.CurrentDomain.DefineDynamicAssembly(new AssemblyName(assemblyName), AssemblyBuilderAccess.Run).DefineDynamicModule(moduleName).DefineType(typeName, TypeAttributes.Public); typeBuilder.DefineDefaultConstructor(MethodAttributes.Public); return typeBuilder; } public static void CreateAutoImplementedProperty(TypeBuilder builder, string propertyName, Type propertyType) { const string PrivateFieldPrefix = "m_"; const string GetterPrefix = "get_"; const string SetterPrefix = "set_"; // Generate the field. FieldBuilder fieldBuilder = builder.DefineField(string.Concat(PrivateFieldPrefix, propertyName), propertyType, FieldAttributes.Private); // Generate the property PropertyBuilder propertyBuilder = builder.DefineProperty(propertyName, PropertyAttributes.HasDefault, propertyType, null); // Property getter and setter attributes. MethodAttributes propertyMethodAttributes = MethodAttributes.Public | MethodAttributes.SpecialName | MethodAttributes.HideBySig; // Define the getter method. MethodBuilder getterMethod = builder.DefineMethod(string.Concat(GetterPrefix, propertyName), propertyMethodAttributes, propertyType, Type.EmptyTypes); // Emit the IL code. // ldarg.0 // ldfld,_field // ret ILGenerator getterILCode = getterMethod.GetILGenerator(); getterILCode.Emit(OpCodes.Ldarg_0); getterILCode.Emit(OpCodes.Ldfld, fieldBuilder); getterILCode.Emit(OpCodes.Ret); // Define the setter method. MethodBuilder setterMethod = builder.DefineMethod(string.Concat(SetterPrefix, propertyName), propertyMethodAttributes, null, new Type[] { propertyType }); // Emit the IL code. // ldarg.0 // ldarg.1 // stfld,_field // ret ILGenerator setterILCode = setterMethod.GetILGenerator(); setterILCode.Emit(OpCodes.Ldarg_0); setterILCode.Emit(OpCodes.Ldarg_1); setterILCode.Emit(OpCodes.Stfld, fieldBuilder); setterILCode.Emit(OpCodes.Ret); propertyBuilder.SetGetMethod(getterMethod); propertyBuilder.SetSetMethod(setterMethod); } }}