分析数值字符串
更新:2010 年 8 月
所有数值类型都具有两种静态分析方法(Parse 和 TryParse),可以使用这些方法将数字的字符串表示形式转换为数值类型。 您可以使用这些方法分析使用 标准数字格式字符串 和 自定义数字格式字符串 中记录的格式字符串生成的字符串。 默认情况下,Parse 和 TryParse 方法可成功地将只包含十进制整数的字符串转换为整数值。 它们可以成功地将包含整数和小数十进制数、组分隔符和小数分隔符的字符串转换为浮点值。 如果操作失败,Parse 方法将引发异常,而 TryParse 方法会返回 false。
分析和格式提供程序
通常,数值的字符串表示形式因区域性而异。 数值字符串的元素都会因区域性而异,包括如货币符号、组(或千位)分隔符、小数分隔符以及货币符号。 分析方法隐式或显式地使用识别这些特定区域性差异的格式提供程序。 如果没有在对 Parse 或 TryParse 方法的调用中指定格式提供程序,将使用与当前线程区域性(由 NumberFormatInfo.CurrentInfo 属性返回的 NumberFormatInfo 对象)相关联的格式提供程序。
格式提供程序由 IFormatProvider 实现表示。 此接口具有一个成员(GetFormat 方法),该成员的唯一参数是表示要设置格式的类型的 Type 对象。 此方法返回提供格式设置信息的对象。 .NET Framework 支持以下两种用于分析数值字符串的 IFormatProvider 实现:
CultureInfo 对象,其 CultureInfo.GetFormat 方法返回提供特定区域性格式设置信息的 NumberFormatInfo 对象。
NumberFormatInfo 对象,其 NumberFormatInfo.GetFormat 方法返回其自身。
以下示例尝试将数组中的每个字符串转换为 Double 值。 它首先尝试使用反映英语(美国)区域性约定的格式提供程序来分析字符串。 如果此操作引发 FormatException,它将尝试使用反映法语(法国)区域性约定的格式提供程序来分析字符串。
Imports System.Globalization
Module Example
Public Sub Main()
Dim values() As String = { "1,304.16", "$1,456.78", "1,094", "152",
"123,45 €", "1 304,16", "Ae9f" }
Dim number As Double
Dim culture As CultureInfo = Nothing
For Each value As String In values
Try
culture = CultureInfo.CreateSpecificCulture("en-US")
number = Double.Parse(value, culture)
Console.WriteLine("{0}: {1} --> {2}", culture.Name, value, number)
Catch e As FormatException
Console.WriteLine("{0}: Unable to parse '{1}'.",
culture.Name, value)
culture = CultureInfo.CreateSpecificCulture("fr-FR")
Try
number = Double.Parse(value, culture)
Console.WriteLine("{0}: {1} --> {2}", culture.Name, value, number)
Catch ex As FormatException
Console.WriteLine("{0}: Unable to parse '{1}'.",
culture.Name, value)
End Try
End Try
Console.WriteLine()
Next
End Sub
End Module
' The example displays the following output:
' en-US: 1,304.16 --> 1304.16
'
' en-US: Unable to parse '$1,456.78'.
' fr-FR: Unable to parse '$1,456.78'.
'
' en-US: 1,094 --> 1094
'
' en-US: 152 --> 152
'
' en-US: Unable to parse '123,45 €'.
' fr-FR: Unable to parse '123,45 €'.
'
' en-US: Unable to parse '1 304,16'.
' fr-FR: 1 304,16 --> 1304.16
'
' en-US: Unable to parse 'Ae9f'.
' fr-FR: Unable to parse 'Ae9f'.
' ' The example displays the following output:
' en-US: 1,304.16 --> 1304.16
'
' en-US: Unable to parse '$1,456.78'.
' fr-FR: Unable to parse '$1,456.78'.
'
' en-US: 1,094 --> 1094
'
' en-US: 152 --> 152
'
' en-US: Unable to parse '123,45 €'.
' fr-FR: Unable to parse '123,45 €'.
'
' en-US: Unable to parse '1 304,16'.
' fr-FR: 1 304,16 --> 1304.16
'
' en-US: Unable to parse 'Ae9f'.
' fr-FR: Unable to parse 'Ae9f'.
using System;
using System.Globalization;
public class Example
{
public static void Main()
{
string[] values = { "1,304.16", "$1,456.78", "1,094", "152",
"123,45 €", "1 304,16", "Ae9f" };
double number;
CultureInfo culture = null;
foreach (string value in values) {
try {
culture = CultureInfo.CreateSpecificCulture("en-US");
number = Double.Parse(value, culture);
Console.WriteLine("{0}: {1} --> {2}", culture.Name, value, number);
}
catch (FormatException) {
Console.WriteLine("{0}: Unable to parse '{1}'.",
culture.Name, value);
culture = CultureInfo.CreateSpecificCulture("fr-FR");
try {
number = Double.Parse(value, culture);
Console.WriteLine("{0}: {1} --> {2}", culture.Name, value, number);
}
catch (FormatException) {
Console.WriteLine("{0}: Unable to parse '{1}'.",
culture.Name, value);
}
}
Console.WriteLine();
}
}
}
// The example displays the following output:
// en-US: 1,304.16 --> 1304.16
//
// en-US: Unable to parse '$1,456.78'.
// fr-FR: Unable to parse '$1,456.78'.
//
// en-US: 1,094 --> 1094
//
// en-US: 152 --> 152
//
// en-US: Unable to parse '123,45 €'.
// fr-FR: Unable to parse '123,45 €'.
//
// en-US: Unable to parse '1 304,16'.
// fr-FR: 1 304,16 --> 1304.16
//
// en-US: Unable to parse 'Ae9f'.
// fr-FR: Unable to parse 'Ae9f'.
分析和 NumberStyles 值
分析操作可处理的样式元素(例如空格、组分隔符和小数分隔符)由 NumberStyles 枚举值定义。 默认情况下,使用 NumberStyles.Integer 值来分析表示整数值的字符串,该值只允许数字、前导和尾随空格以及前导符号。 可使用 NumberStyles.Float 和 NumberStyles.AllowThousands 值的组合来分析表示浮点值的字符串;这种复合样式允许使用数字以及前导和尾随空格、前导符号、小数分隔符、组分隔符以及指数。 通过调用包括 NumberStyles 类型参数的 Parse 或 TryParse 方法的重载,并设置一个或多个 NumberStyles 标记,您可以控制可显示在字符串中的样式元素,以确保分析操作成功。
例如,无法使用 Int32.Parse(String) 方法将包含组分隔符的字符串转换为 Int32 值。但是,如果使用 NumberStyles.AllowThousands 标记,则可成功转换,如以下示例所示。
Imports System.Globalization
Module Example
Public Sub Main()
Dim value As String = "1,304"
Dim number As Integer
Dim provider As IFormatProvider = CultureInfo.CreateSpecificCulture("en-US")
If Int32.TryParse(value, number) Then
Console.WriteLine("{0} --> {1}", value, number)
Else
Console.WriteLine("Unable to convert '{0}'", value)
End If
If Int32.TryParse(value, NumberStyles.Integer Or NumberStyles.AllowThousands,
provider, number) Then
Console.WriteLine("{0} --> {1}", value, number)
Else
Console.WriteLine("Unable to convert '{0}'", value)
End If
End Sub
End Module
' The example displays the following output:
' Unable to convert '1,304'
' 1,304 --> 1304
using System;
using System.Globalization;
public class Example
{
public static void Main()
{
string value = "1,304";
int number;
IFormatProvider provider = CultureInfo.CreateSpecificCulture("en-US");
if (Int32.TryParse(value, out number))
Console.WriteLine("{0} --> {1}", value, number);
else
Console.WriteLine("Unable to convert '{0}'", value);
if (Int32.TryParse(value, NumberStyles.Integer | NumberStyles.AllowThousands,
provider, out number))
Console.WriteLine("{0} --> {1}", value, number);
else
Console.WriteLine("Unable to convert '{0}'", value);
}
}
// The example displays the following output:
// Unable to convert '1,304'
// 1,304 --> 1304
![]() |
---|
分析操作始终使用特定区域性的格式设置约定。如果没有通过传递 CultureInfo 或 NumberFormatInfo 对象来指定区域性,会使用与当前线程相关联的区域性。 |
下表列出了 NumberStyles 枚举的成员并描述了它们对分析操作产生的影响。
NumberStyles 值 |
对要分析的字符串的影响 |
---|---|
仅允许数字。 |
|
允许小数分隔符和小数位。 对于整数值,只允许将零作为小数位。 有效的小数分隔符由 NumberFormatInfo.NumberDecimalSeparator 或 NumberFormatInfo.CurrencyDecimalSeparator 属性确定。 |
|
“e”或“E”字符可用来指示指数计数法。 有关其他信息,请参见 NumberStyles。 |
|
允许前导空格。 |
|
允许尾随空格。 |
|
数字的前面可带有正负号。 |
|
数字的后面可带有正负号。 |
|
可使用括号表示负值。 |
|
允许组分隔符。 组分隔符由 NumberFormatInfo.NumberGroupSeparator 或 NumberFormatInfo.CurrencyGroupSeparator 属性确定。 |
|
允许货币符号。 货币符号由 NumberFormatInfo.CurrencySymbol 属性定义。 |
|
要分析的字符串被解释为十六进制数。 它可以包括十六进制数字 0-9、A-F 和 a-f。 此标记只用来分析整数值。 |
此外,NumberStyles 枚举还提供了以下复合样式,其中包括多个 NumberStyles 标记。
分析和 Unicode 数字
Unicode 标准为各种编写系统中的数字定义了码位。 例如,从 U+0030 到 U+0039 的码位表示从 0 到 9 的基本拉丁文数字,从 U+09E6 到 U+09EF 的码位表示从 0 到 9 的孟加拉文数字,而从 U+FF10 到 U+FF19 的码位表示从 0 到 9 的全角数字。 但是,分析方法唯一识别的数字是基本拉丁文数字 0-9 (码位从 U+0030 到 U+0039)。 如果将数值分析方法传递给包含任何其他数字的字符串,该方法将引发 FormatException。
以下代码示例使用 Int32.Parse 方法来分析由不同编写系统的数字组成的字符串。 正如示例输出所示,虽然尝试分析基本拉丁文数字获得成功,但分析全角、阿拉伯 - 印度文以及孟加拉文数字的尝试将失败。
Module Example
Public Sub Main()
Dim value As String
' Define a string of basic Latin digits 1-5.
value = ChrW(&h31) + ChrW(&h32) + ChrW(&h33) + ChrW(&h34) + ChrW(&h35)
ParseDigits(value)
' Define a string of Fullwidth digits 1-5.
value = ChrW(&hff11) + ChrW(&hff12) + ChrW(&hff13) + ChrW(&hff14) + ChrW(&hff15)
ParseDigits(value)
' Define a string of Arabic-Indic digits 1-5.
value = ChrW(&h661) + ChrW(&h662) + ChrW(&h663) + ChrW(&h664) + ChrW(&h665)
ParseDigits(value)
' Define a string of Bengali digits 1-5.
value = ChrW(&h09e7) + ChrW(&h09e8) + ChrW(&h09e9) + ChrW(&h09ea) + ChrW(&h09eb)
ParseDigits(value)
End Sub
Sub ParseDigits(value As String)
Try
Dim number As Integer = Int32.Parse(value)
Console.WriteLine("'{0}' --> {1}", value, number)
Catch e As FormatException
Console.WriteLine("Unable to parse '{0}'.", value)
End Try
End Sub
End Module
' The example displays the following output:
' '12345' --> 12345
' Unable to parse '12345'.
' Unable to parse '١٢٣٤٥'.
' Unable to parse '১২৩৪৫'.
using System;
public class Example
{
public static void Main()
{
string value;
// Define a string of basic Latin digits 1-5.
value = "\u0031\u0032\u0033\u0034\u0035";
ParseDigits(value);
// Define a string of Fullwidth digits 1-5.
value = "\uFF11\uFF12\uFF13\uFF14\uFF15";
ParseDigits(value);
// Define a string of Arabic-Indic digits 1-5.
value = "\u0661\u0662\u0663\u0664\u0665";
ParseDigits(value);
// Define a string of Bengali digits 1-5.
value = "\u09e7\u09e8\u09e9\u09ea\u09eb";
ParseDigits(value);
}
static void ParseDigits(string value)
{
try {
int number = Int32.Parse(value);
Console.WriteLine("'{0}' --> {1}", value, number);
}
catch (FormatException) {
Console.WriteLine("Unable to parse '{0}'.", value);
}
}
}
// The example displays the following output:
// '12345' --> 12345
// Unable to parse '12345'.
// Unable to parse '١٢٣٤٥'.
// Unable to parse '১২৩৪৫'.
请参见
参考
概念
其他资源
修订记录
日期 |
修订记录 |
原因 |
---|---|---|
2010 年 8 月 |
做了大范围修订。 |
信息补充。 |