Числовые типы с плавающей запятой (справочник по C#)
Числовые типы с плавающей запятой представляют действительные числа. Все числовые типы с плавающей запятой являются типами значений. Они также представляют собой простые типы и могут быть инициализированы литералами. Все числовые типы с плавающей запятой поддерживают арифметические операторы, а также операторы сравнения и равенства.
Характеристики типов с плавающей запятой
C# поддерживает следующие предварительно определенные типы с плавающей запятой:
Ключевое слово или тип C# | Приблизительный диапазон значений | Точность | Размер | Тип .NET |
---|---|---|---|---|
float |
От ±1,5 x 10−45 до ±3,4 x 1038 | 6–9 цифр | 4 байта | System.Single |
double |
от ±5,0 × 10−324 до ±1,7 × 10308 | 15–17 цифр | 8 байт | System.Double |
decimal |
от ±1,0 x 10-28 до ±7,9228 x 1028 | 28-29 знаков | 16 байт | System.Decimal |
В приведенной выше таблице каждый тип ключевого слова C# из крайнего левого столбца является псевдонимом для соответствующего типа .NET. Они взаимозаменяемые. Например, следующие объявления объявляют переменные одного типа:
double a = 12.3;
System.Double b = 12.3;
По умолчанию все типы с плавающей запятой имеют значение 0
. Все типы с плавающей запятой имеют константы MinValue
и MaxValue
с минимальным и максимальными итоговыми значениями этого типа. Типы float
и double
также предоставляют константы, обозначающие бесконечные и нечисловые значения. Например, тип double
предоставляет следующие константы: Double.NaN, Double.NegativeInfinity и Double.PositiveInfinity.
Тип decimal
подходит, если требуемая степень точности определяется числом цифр справа от десятичной запятой. Такие числа обычно используются в финансовых приложениях для денежных сумм (например, 1,00 долл. США), процентных ставок (например, 2,625 %) и т. д. Даже числа, точные только к одной десятичной цифре, обрабатываются более точно decimal
типом: 0,1, например, может быть точно представлен decimal
экземпляром, а double
float
экземпляр не представляет 0,1. Из-за этой разницы в числовых типах в арифметических вычислениях могут возникать непредвиденные ошибки округления при использовании double
или float
для десятичных данных. Вы можете использовать double
вместо decimal
, если оптимизация производительности важнее, чем обеспечение точности. Но любая разница в производительности останется незамеченной для всех приложений, кроме самых требовательных к вычислениям. Еще одна возможная причина, по которой следует избегать decimal
, — это минимальные требования к хранилищу. Например, ML.NET использует float
, так как разница между 4 байтами и 16 байтами суммируется для очень больших наборов данных. Дополнительные сведения см. в разделе System.Decimal.
В одном и том же выражении можно сочетать и целочисленные типы, и типы float
и double
. В этом случае целочисленные типы неявно преобразуются в один из типов с плавающей запятой. При необходимости тип float
неявно преобразуется в double
. Выражение вычисляется следующим образом.
- Если в выражении есть тип
double
, оно оценивается какdouble
илиbool
в реляционных сравнениях или сравнениях на равенство. - Если в выражении нет типа
double
, оно оценивается какfloat
илиbool
в реляционных сравнениях или сравнениях на равенство.
Можно также смешивать целочисленные типы и тип decimal
в выражении. В этом случае целочисленные типы неявно преобразуются в тип decimal
, а выражение вычисляется как decimal
или bool
в реляционных сравнениях и сравнениях на равенство.
Тип decimal
нельзя смешивать с типами float
и double
в выражении. В этом случае, если требуется выполнить арифметические операции или операции сравнения или равенства, необходимо явно преобразовать операнды из типа или в тип decimal
, как показано в следующем примере:
double a = 1.0;
decimal b = 2.1m;
Console.WriteLine(a + (double)b);
Console.WriteLine((decimal)a + b);
Можно использовать строки стандартных числовых форматов или строки пользовательских числовых форматов для форматирования значения с плавающей запятой.
Вещественные литералы
Тип реального литерала определяется его суффиксом следующим образом:
- Литерал без суффикса или с суффиксом
d
илиD
имеет типdouble
. - Литерал с суффиксом
f
илиF
имеет типfloat
. - Литерал с суффиксом
m
илиM
имеет типdecimal
.
В приведенном ниже коде показан пример каждого из них.
double d = 3D;
d = 4d;
d = 3.934_001;
float f = 3_000.5F;
f = 5.4f;
decimal myMoney = 3_000.5m;
myMoney = 400.75M;
В предыдущем примере также показано использование _
в качестве разделителя цифр. Цифровой разделитель можно использовать со всеми видами числовых литералов.
Можно также использовать экспоненциальное представление, то есть указать экспоненту вещественного литерала, как показано в следующем примере:
double d = 0.42e2;
Console.WriteLine(d); // output 42
float f = 134.45E-2f;
Console.WriteLine(f); // output: 1.3445
decimal m = 1.5E6m;
Console.WriteLine(m); // output: 1500000
Преобразования
Существует только одно неявное преобразование между числовыми типами с плавающей запятой: из float
в double
. Однако можно преобразовать любой тип с плавающей запятой в любой другой тип с плавающей запятой с помощьюявного приведения. Для получения дополнительной информации см. статью Встроенные числовые преобразования.
Спецификация языка C#
Дополнительные сведения см. в следующих разделах статьи Спецификация языка C#: