Если это имеет значение в настройке свойства:
decimal? temp = value as decimal?;
value = "90"
Но после отливки temp null...
Каков правильный способ сделать это?
Если это имеет значение в настройке свойства:
decimal? temp = value as decimal?;
value = "90"
Но после отливки temp null...
Каков правильный способ сделать это?
Unboxing работает только в том случае, если тип идентичен! Вы не можете распаковать object
, который не содержит целевое значение. Что вам нужно - это что-то вроде
decimal tmpvalue;
decimal? result = decimal.TryParse((string)value, out tmpvalue) ?
tmpvalue : (decimal?)null;
Это выглядит независимо от того, является ли значение разборным как decimal
. Если да, то назначьте его result
; иначе назначьте null
. Следующий код делает примерно то же самое и может быть проще понять для людей, не знакомых с условным оператором ?:
:
decimal tmpvalue;
decimal? result = null;
if (decimal.TryParse((string)value, out tmpvalue))
result = tmpvalue;
вы должны проанализировать десятичное число. Но если вы хотите, чтобы ваша десятичная дробь была нулевой, если строка неверна, используйте TryParse:
decimal parsedValue;
decimal? temp = decimal.TryParse(value, out parsedValue)
? value
: (decimal?)null;
Таким образом, вы избегаете исключений при анализе плохо сформированных строк.
Почти все примитивные типы предоставляют методы Parse и TryParse для преобразования из строки.
Также рекомендуется передать культуру для аргумента поставщика методу, чтобы избежать проблем с разделителем десятичной дроби. Если вы читаете из другой системы, CultureInfo.InvariantCulture - это, вероятно, путь (но это не значение по умолчанию).
bool TryParse(string s, NumberStyles style,
IFormatProvider provider, out decimal result)
и если вы используете decimal? temp = (decimal?)value;
Если вы не хотите анализировать строки, но хотите, чтобы вы получили либо null
, a decimal
, либо значение NULL decimal
, вы можете сделать что-то вроде этого:
public static Nullable<T> Convert<T>(object input)
where T : struct
{
if (input == null)
return null;
if (input is Nullable<T> || input is T)
return (Nullable<T>)input;
throw new InvalidCastException();
}
Вы можете заставить его возвращать значение null в последней строке вместо этого, если вы хотите избежать исключений, хотя это не будет отличать реальные значения null и плохие приведения.
Обратите внимание, что вам нужно использовать оператор "is", поскольку оператор "as" не работает с типами значений, а кастинг без проверки может вызвать InvalidCastException.
Вы также можете сделать это методом расширения:
public static class ObjectExtensions
{
public static Nullable<T> ToNullable<T>(this object input)
where T : struct
{
if (input == null)
return null;
if (input is Nullable<T> || input is T)
return (Nullable<T>)input;
throw new InvalidCastException();
}
}
И используйте его следующим образом:
object value = 123.45m;
decimal? dec = value.ToNullable<decimal>();
Это поможет избежать предупреждений о сокращении кода о распаковке нулевых ссылок.