与Excel类参考单元格匹配的正则表达式

时间:2016-05-10 02:00:02

标签: javascript regex

我试图制作一个正则表达式,只匹配A-Z(包括)范围之间的字母,后跟0-100(含)之间的数字。如果我的正则表达式之前有任何数字,我不希望它匹配。例如:5A1不匹配,因为前面有数字5,即使A1在字符串中。同样,如果在该范围之后有任何数字值,例如A10000(不应该匹配,因为1000超出100),我不希望它匹配。

下面演示了我想要匹配的内容:

Separated

我一直在尝试使用这些正则表达式,但我不确定如何在该范围之前或之后排除任何数字:

A34A1                // no match
5A1                  // no match
2.344A1              // no match
A1001                // no match
A1                   // match A1
A10                  // match A10
A100                 // match A100
SUM(A1:A2)           // match A1 and A2
SUM(A1:A2, 5A1, A3)  // match A1,A2, A3

5 个答案:

答案 0 :(得分:2)

你走了:

(?:^|[^0-9])([A-Z](?:100|[0-9][0-9]?))(?=$|[^0-9A-Z])

$1将举行您的比赛。

使用示例:

var re = /(?:^|[^0-9])([A-Z](?:100|[0-9][0-9]?))(?=$|[^0-9A-Z])/gim; 

解释

它必须是一行的开头,或者不是数字:

(?:^|[^0-9])

然后,您有一个或两个字母后跟100或一位或两位数字:

([A-Z](?:100|[0-9]?[0-9]))

然后它必须是你的行尾或者不是字母/数字的东西:

(?=$|[^0-9A-Z])

答案 1 :(得分:2)

var regEx = "/([A-Z](\d{1,2}(?!\d)|100))|(SUM\([A-Z](\d{1,2}(?!\d)|100)((:|,)\s?\d{0,}[A-Z](\d{1,2}(?!\d)|100))*\))/g";

匹配A1,A2,Z100 但不是A101或A1000

([A-Z](\d{1,2}(?!\d)|100))
  • 注意:如果没有(?!\d),“A1000”将被识别为“A100”

以SUM开头(并以...结尾)

SUM(.*)

可以有任意数量的“:”或“,”后跟可选的空格和可选数字 匹配SUM(A1:A2,5101,A3)

(:|,)\s?\d{0,}

答案 2 :(得分:2)

使用此正则表达式:

/\b[A-Z]([0-9]{1,2}|100)\b/

或更简单的等价物:

/\b[A-Z]([0-9][0-9]?|100)\b/

或等长的短数字元字符:

/\b[A-Z](\d\d?|100)\b/

在正则表达式的开头和结尾使用\b元字符,可以消除任何不良的前导或尾随字符。 [A-Z]字符类仅包含一个大写字母以启动单元格引用。数字部分由0-99100的交替处理,其中0-99部分由一到两位数的字符类处理。如果这是你的偏好,那么\ d元字符代替明确的[0-9]字符类也可以正常工作。

这是一个示例Ruby程序(与Javascript类似的正则表达式)以显示它的工作原理:

data = [
  [ "A34A1",   false ],
  [ "5A1",     false ],
  [ "2.344A1", false ],
  [ "A1001",   false ],
  [ "A1",      true ],
  [ "A10",     true ],
  [ "A100",    true ],
  [ "SUM(A1:A2)", true ],
  [ "SUM(A1:A2, 5A1, A3)", true ]
]

data.each do |pair|
  puts "#{pair[1] == !(pair[0] =~ /\b[A-Z]([0-9]{1,2}|100)\b/).nil? ? 'Pass' : 'Fail'}: '#{pair[0]}'"
end

data数组中,每对的第二个元素是布尔值,它确定测试单元引用是否匹配。

运行此程序的输出显示所有测试通过:

> ruby regex_test.rb
Pass: 'A34A1'
Pass: '5A1'
Pass: '2.344A1'
Pass: 'A1001'
Pass: 'A1'
Pass: 'A10'
Pass: 'A100'
Pass: 'SUM(A1:A2)'
Pass: 'SUM(A1:A2, 5A1, A3)'

答案 3 :(得分:1)

这不应该比

复杂
/^[A-Z](\d\d?|100)$/

答案 4 :(得分:1)

r = /
    (?<!\d)   # match a digit in a negative lookbehind
    [A-Z]     # match a capital leter
    (?:       # start a non-capture group
      \d{1,2} # match one or two digits
      |       # or
      100     # match string
    )         # end non-capture group
    (?!\d)    # match a non-digit in a negative lookahead
    /x        # free-spacing regex definition mode
通常写的

r = /(?<!\d)[A-Z](?:\d{1,2}|100)(?!\d)/

test = ["A34A1", "5A1", "2.344A1", "A1001", "A1", "A10", "A100",
        "SUM(A1:A2, 5A1, A3)", "A100A", "_A1", "A1_"] 

test.each { |s| puts "#{s} -> #{s.scan(r)}" }
A34A1               -> ["A34"]
5A1                 -> []
2.344A1             -> []
A1001               -> []
A1                  -> ["A1"]
A10                 -> ["A10"]
A100                -> ["A100"]
SUM(A1:A2, 5A1, A3) -> ["A1", "A2", "A3"]
A100A               -> ["A100"]
_A1                 -> ["A1"]
A1_                 -> ["A1"]