匹配数字与正则表达式 - 只有数字和逗号

时间:2010-11-22 13:53:37

标签: .net regex numbers matching

我无法弄清楚如何为示例值构建正则表达式:

123,456,789
-12,34
1234
-8

你能帮帮我吗?

10 个答案:

答案 0 :(得分:472)

答案 1 :(得分:37)

如果您只想允许数字和逗号,^[-,0-9]+$就是您的正则表达式。如果您还想允许空格,请使用^[-,0-9 ]+$

但是,如果你想允许正确的数字,最好使用这样的东西:

^([-+] ?)?[0-9]+(,[0-9]+)?$

或只是使用.net's number parser(对于各种NumberStyles,请参阅MSDN):

try {
    double.Parse(yourString, NumberStyle.Number);
}
catch(FormatException ex) {
    /* Number is not in an accepted format */
}

答案 2 :(得分:9)

试试这个:

^-?\d{1,3}(,\d{3})*(\.\d\d)?$|^\.\d\d$

允许:

1
12
.99
12.34 
-18.34
12,345.67
999,999,999,999,999.99

答案 3 :(得分:6)

由于这个问题已在四年后重新开放,我想提供一个不同的看法。由于有人花了很多时间使用正则表达式,我的观点是:

:一种。如果可能,请勿使用正则表达式验证数字

如果可能,请使用您的语言。可能有一些函数可帮助您确定字符串包含的值是否为有效数字。话虽如此,如果您接受各种格式(逗号等),您可能无法选择。

<强> B中。不要手动编写正则表达式来验证数字范围

  • 编写正则表达式以匹配给定范围内的数字很难。即使将正则表达式写入match a number between 1 and 10,也可能会出错。
  • 一旦你有一个数字范围的正则表达式,它很难调试。首先,看起来很糟糕。其次,你怎么能确定匹配你想要的所有价值而不匹配你不想要的任何价值?坦率地说,如果你自己,没有同行看过去你的肩膀,你不能。最好的调试技术是以编程方式输出整个数字范围,并根据正则表达式进行检查。
  • 幸运的是,有一些工具可以自动为数字范围生成正则表达式。

<强>℃。明智地花费你的正则表达能源:使用工具

  • 给定范围内的匹配数字是已解决的问题。你没有必要尝试重新发明轮子。这是一个问题,可以通过程序以一种保证无差错的方式机械地解决。利用免费搭车。
  • 解决数字范围的正则表达式可能对学习目的很有意思。除此之外,如果你有能力投资于提升你的正则表达能力,那就把它花在有用的东西上,比如加深你对regex greed的理解,阅读Unicode regex,玩零宽度匹配或递归,阅读SO regex FAQ并发现巧妙的技巧,例如如何exclude certain patterns from a regex match ......或阅读经典如 Matering Regular Expressions,3rd Ed The Regular Expressions Cookbook ,第二版

对于工具,您可以使用:

  • 在线:Regex_for_range
  • 离线:我唯一知道的是正则表达专家Jan Goyvaerts RegexMagic(非免费)。它是他的初学者正则表达式产品,我记得它有很多选项来生成给定范围内的数字,以及其他功能。
  • 如果条件过于复杂,则自动生成两个范围...然后使用交替运算符|
  • 将它们连接起来

<强> d。练习:为问题中的规范构建正则表达式

这些规格相当广泛......但不一定含糊不清。让我们再看一下样本值:

123,456,789
-12,34
1234
-8

前两个值如何相关?在第一个中,逗号匹配三个权力组。在第二种情况下,它可能与欧洲大陆式数字格式的小数点相匹配。这并不意味着我们应该允许在任何地方使用数字,例如1,2,3,44。出于同样的原因,我们不应该是限制性的。例如,接受的答案中的正则表达式与其中一个要求123,456,789不匹配(请参阅demo)。

我们如何构建我们的正则表达式来匹配规范?

  • 让我们在^$之间锚定表达式以避免子匹配
  • 允许选择减号:-?
  • 让我们匹配交替(?:this|that)两侧的两种数字:
  • 左侧是欧式数字,带小数部分可选逗号:[1-9][0-9]*(?:,[0-9]+)?
  • 右侧是包含数千个分隔符的数字:[1-9][0-9]{1,2}(?:,[0-9]{3})+

完整的正则表达式:

^-?(?:[1-9][0-9]*(?:,[0-9]+)?|[1-9][0-9]{1,2}(?:,[0-9]{3})+)$

请参阅demo

此正则表达式不允许以0开头的欧式数字,例如0,12。它是一个功能,而不是一个bug。为了匹配这些,我们会做一个小小的调整:

^-?(?:(?:0|[1-9][0-9]*)(?:,[0-9]+)?|[1-9][0-9]{1,2}(?:,[0-9]{3})+)$

请参阅demo

答案 4 :(得分:4)

试试这个:

^-?[\d\,]+$

它将允许一个可选的-作为第一个字符,然后是逗号和数字的任意组合。

答案 5 :(得分:3)

^-?    # start of line, optional -
(\d+   # any number of digits
|(\d{1,3}(,\d{3})*))  # or digits followed by , and three digits
((,|\.)\d+)? # optional comma or period decimal point and more digits
$  # end of line

答案 6 :(得分:2)

^[-+]?(\d{1,3})(,?(?1))*$

Regular expression visualization

Debuggex Demo

那是什么?!

  • ^标记字符串的开头
  • [-+]?在字符串开头后立即允许减去
  • (\d{1,3})在一行中匹配至少一个和最多三个({1,3})个数字(\d - 通常为[0-9])并对它们进行分组(括号内为(...)构建组)作为第一组
  • (,?(?1))*好的......让我们打破这个
    • (...)构建另一个群组(不那么重要
    • ,?在第一个数字序列
    • 后面与逗号(如果存在)匹配
    • (?1)再次匹配第一组的模式(记住(\d{1,3}));在单词中:此时表达式匹配一个符号(加号/减号/无号),后跟一个数字序列,后面跟一个逗号,然后是另一个数字序列。
    • (,?(?1))**尽可能多地重复第二部分(逗号和序列)
  • $最终匹配字符串的结尾

这种表达式的优点是,避免在表达式中一次又一次地定义相同的模式......好吧,缺点有时是复杂性: - /

答案 7 :(得分:0)

在java中,您可以将java.util.ScanneruseLocale方法

一起使用
Scanner myScanner =  new Scanner(input).useLocale( myLocale)

isADouble = myScanner.hasNextDouble()

答案 8 :(得分:-2)

对于例子:

    ^(-)?([,0-9])+$

它应该工作。用你想要的任何语言实现它。

答案 9 :(得分:-2)

试试这个:

    boxValue = boxValue.replace(/[^0-9\.\,]/g, "");

此RegEx将仅匹配数字,点和逗号。