Difference between [0-9] and \ d in tcl

I tried

puts [regexp "(\[0-9]{1,3})\.(\[0-9]{1,3})\.(\[0-9]{1,3})\.(\[0-9]{1,3})" 192.168.1.10]

      

the answer is 1.

But if I use

puts [regexp "(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})" 192.168.1.10]

      

(replaced \[0-9]

by \d

) the answer is 0.

Can someone please tell me why?

+3


source to share


2 answers


You must either strip the backslash in \d

as \\d

when using with double quotes.

puts [regexp "(\\d{1,3})\.(\\d{1,3})\.(\\d{1,3})\.(\\d{1,3})" 192.168.1.10]

      

Or you need to use curly braces.



puts [regexp {(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})} 192.168.1.10]

      

Note. ... Variables will not be replaced with curly braces.

+4


source


The problem here is not the difference between \d

and [0-9]

, but rather how you handle the two expressions in the regex. In Tcl, double quotes allow the first level of substitution. Only when this level of substitution is complete is the result passed to the function regexp

.

So with this view, what is actually passed to the function regexp

in two cases:

([0-9]{1,3}).([0-9]{1,3}).([0-9]{1,3}).([0-9]{1,3})

      

and

(d{1,3}).(d{1,3}).(d{1,3}).(d{1,3})

      

Which clearly doesn't match the line you provided. However, something like dd.ddaddfdd

(remember, .

matches any single character!).

Remember, backslashes are replaced in Tcl as soon as $

or [ ... ]

whenever possible (i.e. when strings are provided without curly braces). To get a literal backslash, you would thus do (with this current formatting):

([0-9]{1,3})\\.([0-9]{1,3})\\.([0-9]{1,3})\\.([0-9]{1,3})

      

and

(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})

      



Or, to avoid the pain of doing this, use curly braces:

regexp {([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})} 192.168.1.10

      

and

regexp {(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})} 192.168.1.10

      


Something else I mentioned here is that you don't need parentheses to check if you don't use them for grouping, so that should be enough and improve the speed of your script:

regexp {[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}} 192.168.1.10

      


And if you want a response to your title, there is a difference between \d

and [0-9]

. The most popular stackoverflow question was raised from C #, but this also applies in Tcl this one which shows that it \d

matches much more than the numbers 0 through 9.

+3


source







All Articles