Я пишу инструмент, который взаимодействует с API для другого программного обеспечения.Часть моего инструмента должна будет генерировать отчеты о различных объектах, найденных через API, и я хочу, чтобы эти отчеты содержали простые строки, идентифицирующие каждый объект.По умолчанию я планирую использовать ToString () для генерации строки для каждого объекта.Однако неудивительно, что я обнаружил, что реализации ToString () по умолчанию в этом API не являются описательными.
Изначально я думал сделать что-то вроде приведенного ниже кода с длинным оператором Switch.Хотя это, скорее всего, станет неуправляемо длинным.
public string GetAPIObjectDescrition(object obj)
{
Type t = obj.GetType();
Switch(t)
{
Case typeof(SomeAPIType):
SomeAPIType x = (SomeAPIType)obj;
return x.SomeProperty;
Case typeof(SomeOtherAPIType):
SomeOtherAPITypex = (SomeOtherAPIType)obj;
return x.SomeOtherProperty;
default:
return x.ToString();
}
}
Далее я попытался использовать методы расширения (см. Код ниже).CustomObjectDescription () работал как положено, но когда я пытался вызвать ToString (), он просто возвращает результаты ToString () по умолчанию.Я никогда раньше не использовал методы расширения, поэтому я мог быть совершенно не в своей тарелке, думая, что что-то подобное даже возможно.
Я не могу гарантировать, что будет расширение CustomObjectDescription () для каждого Типа, встречающегося в APIпоэтому, если я выберу этот маршрут, мне придется каждый раз использовать отражение, чтобы проверить, имеет ли текущий объект расширение GetObjectDescription ().Я хотел бы избегать использования рефлексии, если это вообще возможно.
public static class APIObjectDescriptionExtensions
{
public static string ToString(this APIObject element)
{
return "ElementName = " + element.Name + " ElementID =" + element.Id.IntegerValue.ToString();
}
public static string CustomObjectDescription(this APIObject element)
{
return "ElementName = " + element.Name + " ElementID =" + element.Id.IntegerValue.ToString();
}
}
У кого-нибудь есть какие-либо другие предложения о том, как мне подходить к этой проблеме?Я бы предпочел решение, в котором код для каждого типа API не зависит друг от друга (нет гигантского оператора Switch).
Также, если возможно, я бы хотел, чтобы код строки описания для одного типа наследовался подтипам, если у этих типов нет собственного уникального кода строки описания.
Я думаю, что может быть лучшее решениеэто включает создание пользовательских TypeConverters или, возможно, переопределение / расширение System.Convert.ToString ()?
Обновление
Я думаю, что приведенный ниже пример может помочь прояснить, что япытаюсь сделать.В конечном итоге я хочу иметь возможность взять любой произвольный класс из этого API, тип которого неизвестен до времени выполнения, и сгенерировать строку описания.Если у Типа есть мой собственный метод расширения, его следует использовать, в противном случае код должен возвращаться к простой старой функции ToString ().
public static string GetDataDescription(object o)
{
//get the type of the input object
Type objectType = o.GetType();
//check to see if a description extension method is defined
System.Reflection.MethodInfo extensionMethod = objectType.GetMethod("MyDescriptionExtensionMethod");
if (extensionMethod != null)
{
//if a description extension method was found returt the result
return (string)extensionMethod.Invoke(o, new object[] { });
}
else
{
//otherwise just use ToString();
return o.ToString();
}
}
Этот код выше не работает, хотя методы расширения не найдены GetMethod () .