I have the following code:
public class DataReader<T> where T : class
{
public T getEntityFromReader(IDataReader reader, IDictionary<string, string> FieldMappings)
{
T entity = Activator.CreateInstance<T>();
Type entityType = entity.GetType();
PropertyInfo[] pi = entityType.GetProperties();
string FieldName;
while (reader.Read())
{
for (int t = 0; t < reader.FieldCount; t++)
{
foreach (PropertyInfo property in pi)
{
FieldMappings.TryGetValue(property.Name, out FieldName);
Type genericType = property.PropertyType;
if (!String.IsNullOrEmpty(FieldName))
property.SetValue(entity, reader[FieldName], null);
}
}
}
return entity;
}
}
When I get to a field of type Enum
, or in this case NameSpace.MyEnum
, I want to do something special. I can't simply SetValue
because the value coming from the database is let's say "m" and the value in the Enum
is "Mr". So I need to call another method. I know! Legacy systems right?
So how do I deter开发者_运维技巧mine when a PropertyInfo
item is of a particular enumeration type?
So in the above code I'd like to first check whether the PropertyInfo
type is of a specif enum and if it is then call my method and if not then simply allow SetValue
to run.
Here is what I use with success
property.PropertyType.IsEnum
static void DoWork()
{
var myclass = typeof(MyClass);
var pi = myclass.GetProperty("Enum");
var type = pi.PropertyType;
/* as itowlson points out you could just do ...
var isMyEnum = type == typeof(MyEnum)
... becasue Enums can not be inherited
*/
var isMyEnum = type.IsAssignableFrom(typeof(MyEnum)); // true
}
public enum MyEnum { A, B, C, D }
public class MyClass
{
public MyEnum Enum { get; set; }
}
In your above code,
bool isEnum = typeof(Enum).IsAssignableFrom(typeof(genericType));
will get you whether or not the current type is (derived from) an enum or not.
This is how I handle when I convert a data table into a strongly typed list
/// <summary>
/// Covert a data table to an entity wiht properties name same as the repective column name
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="dt"></param>
/// <returns></returns>
public static List<T> ConvertDataTable<T>(this DataTable dt)
{
List<T> models = new List<T>();
foreach (DataRow dr in dt.Rows)
{
T model = (T)Activator.CreateInstance(typeof(T));
PropertyDescriptorCollection properties = TypeDescriptor.GetProperties(typeof(T));
foreach (PropertyDescriptor prop in properties)
{
//get the property information based on the type
System.Reflection.PropertyInfo propertyInfo = model.GetType().GetProperties().Last(p => p.Name == prop.Name);
var ca = propertyInfo.GetCustomAttribute<PropertyDbParameterAttribute>(inherit: false);
string PropertyName = string.Empty;
if (ca != null && !String.IsNullOrWhiteSpace(ca.name) && dt.Columns.Contains(ca.name)) //Here giving more priority to explicit value
PropertyName = ca.name;
else if (dt.Columns.Contains(prop.Name))
PropertyName = prop.Name;
if (!String.IsNullOrWhiteSpace(PropertyName))
{
//Convert.ChangeType does not handle conversion to nullable types
//if the property type is nullable, we need to get the underlying type of the property
var targetType = IsNullableType(propertyInfo.PropertyType) ? Nullable.GetUnderlyingType(propertyInfo.PropertyType) : propertyInfo.PropertyType;
// var propertyVal = Convert.ChangeType(dr[prop.Name], targetType);
//Set the value of the property
try
{
if (propertyInfo.PropertyType.IsEnum)
prop.SetValue(model, dr[PropertyName] is DBNull ? (object)null : Enum.Parse(targetType, Convert.ToString(dr[PropertyName])));
else
prop.SetValue(model, dr[PropertyName] is DBNull ? (object)null : Convert.ChangeType(dr[PropertyName], targetType));
}
catch (Exception ex)
{
//Logging.CustomLogging(loggingAreasType: LoggingAreasType.Class, loggingType: LoggingType.Error, className: CurrentClassName, methodName: MethodBase.GetCurrentMethod().Name, stackTrace: "There's some problem in converting model property name: " + PropertyName + ", model property type: " + targetType.ToString() + ", data row value: " + (dr[PropertyName] is DBNull ? string.Empty : Convert.ToString(dr[PropertyName])) + " | " + ex.StackTrace);
throw;
}
}
}
models.Add(model);
}
return models;
}
精彩评论