Преобразовать ссылочные примитивы в универсальный тип - PullRequest
2 голосов
/ 06 февраля 2012

Я знаю, что название сбивает с толку, поэтому я попытаюсь объяснить лучше.Вот в основном то, что я хочу сделать внутри метода:

if (record["id"] != DBNull.Value) _id = Convert.ToInt32(record["id"]);
else id = -1;

Я хочу, чтобы это работало для нескольких типов, которые я сохранил в своей базе данных.(Так что, если это строка, она преобразует ее в строку и так далее).Любой способ сделать это хорошо, и я пытался сделать это с помощью метода.Я получил это далеко, но C # не будет автоматически конвертировать int в объект.Идеи?

    private void Load(ref object var, object obj, object def)
    {
        if (var is int)
        {
            var = Convert.ToInt32(obj);
        }
    }

   int _id;
   Load(ref _id, record["id"], -1);

Просто, чтобы уточнить, моя ошибка: «не могу преобразовать из ref int в ref объект».Спасибо за любую помощь.

Ответы [ 2 ]

3 голосов
/ 06 февраля 2012

Вы можете использовать Convert.ChangeType() и сделать свой метод общим:

private void Load<T, U>(out T value, U obj, T defaultValue)
{
    if (obj is DBNull)
       value = defaultValue;
    else
        value = (T)Convert.ChangeType(obj, typeof(T));
}

Теперь вы можете просто использовать его вот так (упрощенный пример, не уверен, что вам нужно defдля):

int id;
object foo = 42;
Load(out id, foo, 1);
1 голос
/ 06 февраля 2012

Прежде всего, var - зарезервированное слово в C # 3.0 и выше (VS 2008 и более поздние версии).

Более того, я бы попытался настроить это как универсальный; таким образом, ваш метод может обнаружить истинные типы переменных, которые вы передаете, и работать с ними в каждом конкретном случае, как если бы они были строго типизированы:

private void Load<TVar, TSet>(ref TVar var, TSet obj, TVar def)
{
    //this is a little heavy-handed, but in pretty much any situation where 
    //this can fail, you just want the basic type.
    try
    {
       if (var is IConvertible && obj is IConvertible)
          var = (TVar)Convert.ChangeType(obj, typeof(TVar));
       else
          var = (TVar)obj; //there may just be an explicit operator
    }
    catch(Exception) 
    {
       var = def; //defined as the same type so they are always assignable
    }
}
...