Как передать строку в функцию, требующую объекта?
Я использую Chello (оболочку C# для Trello API). Мне нужно передать аргумент "createCard" в соответствии с документацией здесь: https://trello.com/docs/api/card/index.html
И это функция, которую я использую от Chello:
public IEnumerable<CardUpdateAction> ForCard(string cardId, object args)
{
string queryString = BuildQueryString(args);
return GetRequest<List<CardUpdateAction>>("/cards/{0}/actions?{1}", cardId, queryString);
}
Я попытался назвать это так:
List<CardUpdateAction> cua = chello.CardUpdates.ForCard("5264d37736695b2821001d7a","createCard").ToList();
но я получаю ошибку: Несоответствие параметров счетчика
по этой функции:
protected static string BuildQueryString(object args)
{
string queryString = String.Empty;
if (args != null)
{
StringBuilder sb = new StringBuilder();
foreach (var prop in args.GetType().GetProperties())
{
sb.AppendFormat("{0}={1}&", prop.Name, prop.GetValue(args, null));
}
if (sb.Length > 0) sb.Remove(sb.Length - 1, 1);
queryString = sb.ToString();
}
return queryString;
}
2 ответа
Проблема в том, что используемый вами API ожидает, что вы передадите класс, который имеет общедоступные свойства, равные тегам, которые вы хотите использовать.
Это очень легко сделать с помощью анонимных типов (я делаю немного другой пример, чтобы проиллюстрировать точку)
//This will cause BuildQueryString to return "actions=createCard&action_fields=data,type,date"
var options = new { actions = "createCard", action_fields = "data,type,date" };
List<CardUpdateAction> cua = chello.CardUpdates.ForCard("5264d37736695b2821001d7a",options).ToList();
string
является object
, Каждый тип платформы.NET наследуется от Object
, Это называется Unified Type System.
С другой стороны, у нас есть принцип подстановки Лискова, который просто говорит, что если B является подтипом A (B является A), то вы должны иметь возможность использовать B везде, где используется A.
Исходя из этих причин, вы можете передать строку любому методу, который принимает объект в качестве аргумента.
Вы можете проверить это:
public void DoSomething(object args)
{
}
public void Main()
{
DoSomething("some string argument, instead of the object");
}
Работает просто отлично. Нет ошибок.