Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 有什么方法可以改进这个正则表达式吗?_Javascript_Regex - Fatal编程技术网

Javascript 有什么方法可以改进这个正则表达式吗?

Javascript 有什么方法可以改进这个正则表达式吗?,javascript,regex,Javascript,Regex,我对正则表达式有点生疏,所以希望能得到一些同行的反馈。它将在我的网站上大量使用,因此任何奇怪的边缘案例都可能造成严重破坏。其思想是在配方中输入一定量的成分,以整单位或分数表示。由于我的自动完成机制,只有一个数字也是有效的(因为它会弹出一个下拉列表)。这些行是有效的: 1 1/2 1 1/2 4 cups 4 1/2 cups 10 3/4 cups sliced 行的数字部分应该是它自己的组,这样我就可以用分数解析器来解析它。数字部分后面的所有内容都应该是第二组。起初,我尝试了以下方法: ^\

我对正则表达式有点生疏,所以希望能得到一些同行的反馈。它将在我的网站上大量使用,因此任何奇怪的边缘案例都可能造成严重破坏。其思想是在配方中输入一定量的成分,以整单位或分数表示。由于我的自动完成机制,只有一个数字也是有效的(因为它会弹出一个下拉列表)。这些行是有效的:

1
1/2
1 1/2
4 cups
4 1/2 cups
10 3/4 cups sliced
行的数字部分应该是它自己的组,这样我就可以用分数解析器来解析它。数字部分后面的所有内容都应该是第二组。起初,我尝试了以下方法:

^\s*(\d+|\d+\/\d+|\d+\s*\d+\/\d+)\s*(.*)$
这几乎是可行的,但是“1 1/2杯”将被解析为(1)(1/2杯),而不是(1 1/2)和(杯)。我搔了搔头之后,确定这是因为我的“OR”子句的顺序。(1) 满足\d+且(.*)满足其余部分。所以我把它改成:

^\s*(\d+\/\d+|\d+\s*\d+\/\d+|\d+)\s*([a-z].*)$
这几乎是可行的,但允许出现“1 1/2/4杯”或“1/2 3杯”之类的怪异现象。因此,我决定强制将字母作为有效数字表达式后的第一个字符:

^\s*(\d+\/\d+|\d+\s*\d+\/\d+|\d+)\s*($|[a-z].*)$
注意,我是在不区分大小写的模式下运行的。以下是我的问题:

  • 这个表达可以改进吗?我有点不喜欢数字、分数、复合分数的“或”列表,但我想不出一种允许整数、分数或复合分数的方法

  • 如果我能在数字部分之后为每个单词返回一个组,那就太好了。例如一组(10 3/4)、一组(杯子)和一组(切片)。后面可以有任意数量的单词。这可能吗


  • 谢谢

    好吧,在我看来,你根本不需要任何条件(但见下文)

    对于数字位,您可以忽略以下内容:

    \d+(\s+\d+/\d+)
    
    它可以处理所有的分数

    我仍然会用OR子句来分隔小数点,因为这可能会使事情复杂化。因此,我认为你可能会通过以下方式逃脱:

    ^\s*((\d+\s)?(\d+/\d+)?|\d+(\.\d+)?)\s*([a-z].*)?$
     |   |                  |           |  |
     |   |                  |           |  +--- start of alpha section.
     |   |                  |           +------ optional white space.
     |   |                  +------------------ decimal (nn[.nn])
     |   +------------------------------------- fractional ([nn ][nn/nn])
     +----------------------------------------- optional starting space.
    
    虽然这允许一个空的分数金额,所以你可能会更好地利用你所拥有的(在单独的OR子句中的整数、分数和小数)

    我更喜欢
    ([a-z].*)$
    结构,而不是
    ($|[a-z].*)$
    我自己,但这可能只是我过去对在RE:-)中有多个行尾标记的厌恶。)


    但是,老实说,我想你可能想用热核弹头打苍蝇


    您真的需要限制输入的内容吗。我见过一些食谱,它们需要
    一小撮盐
    一把苏丹娜
    。我个人认为你可能对你所允许的限制太多了。我会有一个用于数量的自由格式字段和一个用于食品类型的下拉列表(实际上,我可能只允许该批次的自由格式,除非我提供了根据冰箱中的内容搜索食谱的功能)。

    我相信这个正则表达式应该满足您的要求:

    /^\s*(\d+ \d+\/\d+|\d+\/\d+|\d+)\s*(.*)/
    

    为了匹配特定的单词,您应该在解析之后对空格进行拆分。有些事情你不想用正则表达式做;)

    哎呀,又错过了一个案子。。金额可以用十进制表示。因此,我又添加了一个OR子句:^\s*(\d+\/\d+\d+\s*\d+\/\d+\d+\d*.\d)\s*($[a-z].*)也许我们使用的是不同的解析器,但这与我上面的任何示例都不匹配。。但是我想我明白你想用问号做什么了。@Mike,我对Javascript引擎没有我所希望的那么熟悉,但我希望描述性的部分能够理解这个想法。是的,看看你的表达,我认为它也应该起作用,但出于某些原因,它没有:)我正在使用regextster.com来测试东西。至于你的第二点,为什么我不允许自由形式的量,我的整个网站围绕着绘制食谱之间的关系图和转换各种成分的能力(3/4杯切碎的奶酪有多少盎司,等等)。你可以做一些事情,比如加入你所拥有的成分和数量,以及你想要多少份食谱,它会告诉你用它可以制作出最有效的一套食谱。由于这个原因,配料是/高度/标准化的。是的,从用户界面的角度看很糟糕,但这是我的挑战,让它尽可能简单。@Mike,这不是一个坏主意,它在另一方面会很有用。我曾多次咒骂烹饪书的作者,因为他们让我量出10液盎司的东西,然后我问“那是用毫升表示的吗?”然后我不得不去找一张换算表。您可能会发现以公制(或英制,无论您喜欢什么)存储所有内容并允许用户选择其表示单位非常有用。这样,即使数据库可能会说10液体盎司,用户看到的只是他们知道的测量值。当然,这与你的问题无关,但我愿意为这个功能付钱。是的,这很有效,只是没有小数点支持。。我将(.*)改为([a-z].*)以摆脱1/2/杯之类的东西。实际上,$|[a-z].*)可能更好,因为我不想在数字部分之后要求任何东西。啊,是的。如果需要十进制支持,则应使用
    [\d.]+
    。但是,如果您想添加复杂的规则,很难将其完全包含在一个正则表达式中。基于上述注释,我决定([a-z].*)?比我的方式更好:)