Я использую следующий метод для создания объекта посредством отражения
Activator.CreateInstance(Type type, params object[] parameters)
Где "параметры" - это список параметров, переданных конструктору во время выполнения.
Тем не менее, я хотел бы, чтобы этот процесс был более интуитивным для других разработчиков в команде и вместо того, чтобы передавать массив объектов [], я хотел бы, чтобы они передавали анонимный объект, например
// note, invalid code
Activator.CreateInstance(typeof(MyType), new { paramName1 = "abc", paramName2 = "xyz})
Поскольку метод framework не поддерживает его, имеет ли кто-нибудь пример кода, который переводит анонимный объект в массив? Обратите внимание, что порядок параметров важен для метода Activator.CreateInstance(), так как он выполняет сопоставление параметров. Очевидно, что это склонность к ошибкам, поэтому я предпочел бы использовать анонимный тип.
Любые предложения с удовольствием оценены.
Алек.
Для этого я бы не использовал Activator.CreateInstance
. Я бы использовал Type.GetConstructors()
чтобы получить все конструкторы, а затем найти тот, который имеет такое же количество параметров, что и у анонимного типа, и с теми же именами. Если может быть несколько таких конструкторов с разными типами, вам нужно добавить дополнительную логику, чтобы проверить, что каждый тип параметра совместим с соответствующим типом свойства.
Что-то вроде:
public object CreateInstance(Type type, Object parameterMapping)
{
var ctors = type.GetConstructors();
var properties = parameterMapping.GetType().GetProperties();
foreach (var ctor in ctors)
{
var parameters = ctor.GetParameters();
if (parameters.Length != properties.Length)
{
continue;
}
object[] args = new object[parameters.Length];
bool success = true;
for (int i = 0; i < parameters.Length;
{
var property = parameterMapping.GetType().GetProperty(parameter.Name);
if (property == null)
{
success = false;
break;
}
// TODO: Check property type is appropriate too
args[i] = property.GetValue(parameterMapping, null);
}
if (!success)
{
continue;
}
return ctor.Invoke(args);
}
throw new ArgumentException("No suitable constructor found");
}