about_Numeric_Literals

简短说明

本文介绍 PowerShell 中数值的语法和用法。

详细说明

有两种类型的数值文本:整数和实数。 两者都可以具有类型和乘数后缀。

整数文本

整数文本可以采用十进制、十六进制或二进制表示法编写。 十六进制文本以 0x 为前缀,二进制文本的前缀为 0b,以将它们与十进制数区分开来。

整数文本可以具有类型后缀和乘数后缀。

后缀 意义 注意
y 已签名字节数据类型 在 PowerShell 6.2 中添加
uy unsigned byte 数据类型 在 PowerShell 6.2 中添加
s 短数据类型 在 PowerShell 6.2 中添加
us 无符号短数据类型 在 PowerShell 6.2 中添加
l long 数据类型
u unsigned int 或 long 数据类型 在 PowerShell 6.2 中添加
ul 无符号长数据类型 在 PowerShell 6.2 中添加
n BigInteger 数据类型 在 PowerShell 7.0 中添加
kb kibibyte (10241) 乘数
mb mebibyte (10242) 乘数
gb gigibyte (10243) 乘数
tb teribyte (10244) 乘数
pb petibyte (10245) 乘数

整数文本的类型由其值、类型后缀和数值乘数后缀确定。

对于没有类型后缀的整数文本:

  • 如果值可以由类型 [int]表示,则为其类型。
  • 否则,如果值可以按类型 [long]表示,则为其类型。
  • 否则,如果值可以按类型 [decimal]表示,则为其类型。
  • 否则,它由类型 [double]表示。

对于类型后缀为整数文本:

  • 如果类型后缀为 u,并且值可以按类型 [uint] 表示,则其类型 [uint]
  • 如果类型后缀为 u,并且值可以按类型 [ulong] 表示,则其类型 [ulong]
  • 如果其值可以按指定类型表示,则为其类型。
  • 否则,该文本的格式不正确。

实际文本

实际文本只能用十进制表示法编写。 此表示法可以包括小数点后面的小数点和使用指数部分的科学表示法。

指数部分包括一个“e”,后跟一个可选符号(+/-)和一个表示指数的数字。 例如,文本值 1e2 等于数值 100。

实际文本可以具有类型后缀和乘数后缀。

后缀 意义
d 十进制数据类型
kb kibibyte (10241) 乘数
mb mebibyte (10242) 乘数
gb gigibyte (10243) 乘数
tb teribyte (10244) 乘数
pb petibyte (10245) 乘数

有两种类型的实际文本:double 和 decimal。 这些由小数类型后缀的缺失或存在分别指示。 PowerShell 不支持 [float] 值的文字表示形式。 双实文字的类型 [double]。 小数实文本的类型 [decimal]。 小数实文本的分数部分尾随零是重要的。

如果 [double] 实文本中指数部分的数字值小于支持的最小值,则 [double] 实际文本的值为 0。 如果 [decimal] 实际文本中指数部分的位数的值小于支持的最小值,则文本格式不正确。 如果 [double][decimal] 实际文本中指数部分的位数的值大于支持的最大值,则文本格式不正确。

注意

该语法允许双实文本具有长类型后缀。 PowerShell 将此情况视为一个整数文本,其值由类型 [long]表示。 此功能已保留,以便与早期版本的 PowerShell 向后兼容。 但是,不建议程序员使用此形式的整数文本,因为它们可以轻松掩盖文本的实际值。 例如,1.2L 具有值 1,1.2345e1L 值为 12,1.2345e-5L 值为 0,其中没有一个立即明显。

数字乘数

为方便起见,整数和实际文本可以包含数字乘数,这表示一组常用幂 2 之一。 数字乘数可以用大写字母或小写字母的任意组合编写。

乘数后缀可以与任何类型后缀结合使用,但在类型后缀之后必须存在。 例如,文本 100gbL 格式不正确,但文本 100Lgb 有效。

如果乘数创建的值超出了后缀指定的数值类型的可能值,则文本格式不正确。 例如,文本 1usgb 格式不正确,因为值 1gb 大于 [ushort] 后缀指定的 us 类型所允许的值。

乘数示例

PS> 1kb
1024

PS> 1.30Dmb
1363148.80

PS> 0x10Gb
17179869184

PS> 1.4e23tb
1.5393162788864E+35

PS> 0x12Lpb
20266198323167232

数值类型加速器

PowerShell 支持以下类型加速器:

加速器 注意 描述
[byte] 字节 (未签名)
[sbyte] 字节(已签名)
[int16] 16 位整数
[short] [int16] 的别名 16 位整数
[uint16] 16 位整数(无符号)
[ushort] [uint16] 的别名 16 位整数(无符号)
[int32] 32 位整数
[int] [int32] 的别名 32 位整数
[uint32] 32 位整数(无符号)
[uint] [uint32] 的别名 32 位整数(无符号)
[int64] 64 位整数
[long] [int64] 的别名 64 位整数
[uint64] 64 位整数(无符号)
[ulong] [uint64] 的别名 64 位整数(无符号)
[bigint] 请参阅 bigInteger 结构
[single] 单精度浮点
[float] [single] 的别名 单精度浮点
[double] 双精度浮点
[decimal] 128 位浮点

注意

PowerShell 6.2 中添加了以下类型加速器:[short][ushort][uint][ulong]

例子

下表包含数值文本的几个示例,并列出了其类型和值:

类型 价值
100 Int32 100
100u UInt32 100
100D 十进制 100
100l Int64 100
100uL UInt64 100
100us UInt16 100
100uy 字节 100
100y SByte 100
1e2 100
1.e2 100
0x1e2 Int32 482
0x1e2L Int64 482
0x1e2D Int32 7725
482D 十进制 482
482gb Int64 517543559168
482ngb BigInteger 517543559168
0x1e2lgb Int64 517543559168
0b1011011 Int32 91
0xFFFF Int16 -1
0xFFFFFFFF Int32 -1
-0xFFFFFFFF Int32 1
0xFFFFFFFFu UInt32 4294967295

使用二进制或十六进制数字

如果指定了 [bigint] 后缀,则过大二进制或十六进制文本可以返回为 n 而不是失败分析。 但是,即使 [decimal] 范围,符号位仍然受到以上尊重:

  • 如果二进制字符串长度为 8 位的倍数,则最高位被视为符号位。
  • 如果十六进制字符串的长度为 8 的倍数,则第一个数字为 8 或更高,则数字被视为负数。

在二进制和十六进制文本上指定无符号后缀会忽略符号位。 例如,0xFFFFFFFF 返回 -1,但 0xFFFFFFFFu 返回4294967295的 [uint]::MaxValue

在 PowerShell 7.1 中,对十六进制文本使用类型后缀现在返回该类型的有符号值。 例如,在 PowerShell 7.0 中,表达式 0xFFFFs 返回错误,因为正值对于 [int16] 类型来说太大。 PowerShell 7.1 将此解释为 -1 类型的 [int16]

使用 0 为文本添加前缀将绕过它,并被视为无符号。 例如:0b011111111。 当在 [bigint] 范围内处理文本时,这是必需的,因为无法组合 un 后缀。

还可以使用 - 前缀来否定二进制和十六进制文本。 这可能会导致正数,因为允许签名位。

BigInteger 后缀数字接受符号位:

  • BigInteger 后缀十六进制将长度为 8 个字符的任意文本的高位视为符号位。 长度不包括 0x 前缀或任何后缀。
  • BigInteger 后缀二进制文件接受 96 和 128 个字符的符号位,并在之后的每 8 个字符接受一次。

数值类型转换

当字符串转换为数字时,支持其他十六进制格式指示器。 这些附加格式不能识别为文本。

[int] '0xF' -eq 0xF
[int] '&hF' -eq 0xF
[int] '#F' -eq 0xF
[int] '0b1111' -eq 0b1111
[int] '0b1111' -eq 15

类似于数字文本的命令

任何看起来像有效数值文本的命令都必须使用调用运算符(&)执行,否则它将解释为数字。 格式不正确的文本(如 1usgb)将导致以下错误:

PS> 1usgb
At line:1 char:6
+ 1usgb
+      ~
The numeric constant 1usgb is not valid.
+ CategoryInfo          : ParserError: (:) [], ParentContainsErrorRecordException
+ FullyQualifiedErrorId : BadNumericConstant

但是,具有无效语法(如 1gbus)的格式不正确的文本将被解释为标准裸字符串,并且可以在调用命令的上下文中解释为有效的命令名称。

访问数值对象的属性和方法

若要访问数值文本的成员,需要将文本括在括号中时,在某些情况下。

  • 文本没有小数点
  • 文本在小数点之后没有任何数字
  • 文本没有后缀

例如,以下示例失败:

PS> 2.GetType().Name
At line:1 char:11
+ 2.GetType().Name
+           ~
An expression was expected after '('.
+ CategoryInfo          : ParserError: (:) [], ParentContainsErrorRecordException
+ FullyQualifiedErrorId : ExpectedExpression

以下示例工作:

PS> 2uL.GetType().Name
UInt64
PS> 1.234.GetType().Name
Double
PS> (2).GetType().Name
Int32

前两个示例无需将文本值括在括号中,因为 PowerShell 分析器可以确定数值文本结束的位置,GetType 方法开始。

PowerShell 如何分析数值文本

PowerShell v7.0 更改了对数值文本进行分析的方式,以启用新功能。

分析实际数值文本

如果文本包含小数点或电子表示法,则文本字符串将分析为实数。

  • 如果存在十进制后缀,则直接进入 [decimal]
  • 否则,分析为 [double],并将乘数应用于值。 然后检查类型后缀并尝试转换为适当的类型。
  • 如果字符串没有类型后缀,则分析为 [double]

分析整数数字文本

使用以下步骤分析整数类型文本:

  1. 确定弧度格式
    • 对于二进制格式,请分析为 [bigint]
    • 对于十六进制格式,使用特殊情况分析为 [bigint],以便在值位于 [int][long] 范围内时保留原始行为。
    • 如果二进制和十六进制都不是,则通常解析为 [bigint]
  2. 在尝试任何强制转换之前应用乘数值,以确保可以在不溢出的情况下适当检查类型边界。
  3. 检查类型后缀。
    • 检查类型边界并尝试分析到该类型。
    • 如果未使用后缀,则值按以下顺序进行边界检查,导致第一次成功测试确定数字的类型。
      • [int]
      • [long]
      • [decimal] (仅 base-10 文本)
      • [double] (仅 base-10 文本)
    • 如果该值超出十六进制和二进制数 [long] 范围,则分析将失败。
    • 如果该值超出 10 基数的 [double] 范围,则分析将失败。
    • 必须使用 n 后缀显式写入较高值,才能将文本分析为 BigInteger

分析大值文本

以前,在强制转换为任何其他类型之前,将更高的整数值分析为双精度值。 这会导致较高的范围中的精度损失。 例如:

PS> [bigint]111111111111111111111111111111111111111111111111111111
111111111111111100905595216014112456735339620444667904

若要避免此问题,必须以字符串的形式写入值,然后转换它们:

PS> [bigint]'111111111111111111111111111111111111111111111111111111'
111111111111111111111111111111111111111111111111111111

在 PowerShell 7.0 中,必须使用 N 后缀。

PS> 111111111111111111111111111111111111111111111111111111n
111111111111111111111111111111111111111111111111111111

此外,应使用小数后缀 [ulong]::MaxValue 来表示 [decimal]::MaxValueD 之间的值,以保持准确性。 如果没有后缀,这些值将使用实际分析模式分析为 [double]