I created a regular expression that would match 2 numbers in any order from a four digit number. I am trying to create a regular expression that can math 3 numbers out of a four digit number in any order. Below is what I currently use to match two numbers:
regEx01 = re.compile(r'\b[0-9]*(?:0[0-9]*[0-9]?1|1[0-9]*[0-9]?0)[0-9]*\b')
Matches 0 and 1 in 7019, 8019, 2160.
Future regular expression must match 0, 1 and 2.
7012 positive
0190 negative
9201 positive
1226 negative
Any direction will be greatly appreciated.
You may use a regex based on positive lookaheads to make it concise:
\b(?=\d*0)(?=\d*1)(?=\d*2)\d+\b
See the regex demo.
Details
\b - word boundary
(?=\d*0) - a positive lookahead that requires a 0 after zero or more digits
(?=\d*1) - requires 1
(?=\d*2) - requires 2
\d+ - 1+ digits
\b - word boundary
Or, to increase performance, replace \d*s with "subtracted" values:
r'\b(?=[1-9]*0)(?=[02-9]*1)(?=[013-9]*2)\d+\b'
See this regex demo
Here, (?=[1-9]*0) quickly checks if there is a 0 after 0+ digits from 1 to 9, (?=[02-9]*1) checks for 1 and (?=[013-9]*2) checks for 2 in a similar way.
Related
I am trying to write a regex pattern for phone numbers consisting of 9 fixed digits.
I want to identify numbers that have two numbers alternating for four times such as 5XYXYXYXY
I used the below sample
number = 561616161
I tried the below pattern but it is not accurate
^5(\d)(?=\d\1).+
can someone point out what i am doing wrong?
I would use:
^(?=\d{9}$)\d*(\d)(\d)(?:\1\2){3}\d*$
Demo
Here is an explanation of the pattern:
^ from the start of the number
(?=\d{9}$) assert exactly 9 digits
\d* match optional leading digits
(\d) capture a digit in \1
(\d) capture another digit in \2
(?:\1\2){3} match the XY combination 3 more times
\d* more optional digits
$ end of the number
If you want to repeat 4 times 2 of the same pairs and matching 9 digits in total:
^(?=\d{9}$)\d*(\d\d)\1{3}\d*$
Explanation
^ Start of string
(?=\d{9}$) Positive lookahead, assert 9 digits till the end of the string
\d* Match optional digits
(\d\d)\1{3} Capture group 1, match 2 digits and then repeat what is captured in group 1 3 times
\d* Match optional digits
$ End of string
Regex demo
If you want to match a pattern repeating 4 times 2 digits where the 2 digits are not the same:
^(?=\d{9}$)\d*((\d)(?!\2)\d)\1{3}\d*$
Explanation
^ Start of string
(?=\d{9}$) Positive lookahead, assert 9 digits till the end of the string
\d* Match optional digits
( Capture group 1
(\d) Capture group 2, match a single digit
(?!\2)\d Negative lookahead, assert not the same char as captured in group 2. If that is the case, then match a single digit
) Close group 1
\1{3} Repeat the captured value of capture group 1 3 times
\d* Match optional digits
$ End of string
Regex demo
My first guess from OP's self tried regex ^5(\d)(?=\d\1).+ without any own additions was a regex is needed to verify numbers starting with 5 and followed by 4 pairs of same two digits.
^5(\d\d)\1{3}$
Demo at regex101
The same idea with the "added guess" to disallow all same digits like e.g. 511111111
^5((\d)(?!\2)\d)\1{3}$
Demo at regex101
Guessing further that 5 is a variable value and assuming if one variable at start/end with the idea of taking out invalid values early - already having seen the other nice provided answers.
^(?=\d?(\d\d)\1{3})\d{9}$
Demo at regex101
Solution 3 with solution 2's assumption of two different digits in first pairing.
^(?=\d?((\d)(?!\2)\d)\1{3})\d{9}$
Demo at regex101
Solutions 3 and 4 are most obvious playings with #4thBird's nice answer in changed order.
I want to test a number consisting of 9 fixed digits.
The number consists of 7 consecutive numbers in the middle. I want to ignore the first and last character. The pattern is 5YYYYYYYX
I am testing my regex using the below sample
577777773
I was able to write a regex that catches the middle 7 numbers. But i want to exclude the first and last character.
(?<!^)([0-9])\1{7}(?!$)
Any advice on how to do this
You could write the pattern as:
(?<=^\d)(\d)\1{6}(?=\d$)
Explanation
(?<=^\d) Assert a digit at the start of the string to the left
(\d) Capture a digit in group 1
\1{6} Repeat the captured value in group 1 six times
(?=\d$) Assert a digit at the end of the string to the right
See a regex demo.
Or a capture group variant instead of lookarounds:
^\d((\d)\2{6})\d$
See another regex demo.
If the patterns should not be bounded to the start and the end of the string, you can use word boundaries \b on the left and right instead of ^ and $
To match 7 consecutive digits in the middle, and the first and last char can not be the same as the consecutive ones:
^(?!(\d)\1)\d((\d)\3{6})(?!\3)\d$
Explanation
^ Start of string
(?!(\d)\1) Negative lookahead, assert not 2 of the same numbers at the start by capturing a single digit in group 1 and matching the same digit directly after it
\d Match a single digit (the first one)
( Capture group 2
(\d)\3{6} Capture a digit in group 3, and repeat that 6 times after it
) Close group 2
(?!\3)\d Match the last digit when it is not the same as the 7 preceding digits
$ End of string
See a regex demo.
The value of the 7 consecutive digits are in group 2
You may use this alternative solution using \B (not a word boundary):
\B(\d)\1{6}\B
RegEx Demo
RegEx Breakup:
\B: Inverse of word boundary
(\d): Match a digit and capture in group #1
\1{6}: Match 6 more occurrences of same digit captured in group #1
\B: Inverse of word boundary
I am trying to create a regular expression that works for the different types of height inputs, it should work for the following examples below:
5-10
5-09
5-9
6'
6'0
5'9"
5'09"
5'9
5'09
I don't need to consider values below 4'0 or above 6'11.
Here's my regular expression so far:
[456][-']\d{1,2}"?
I need to make the " not work if there is a - between feet and inches.
Also, for the inches part, I am currently allowing for either 1 or 2 digits, when I really only want to allow for two digits when the first digit is a 0 or 1, and if it is 1, the second digit can only be 0 or 1.
For example, 00-09 should work but and 10 and 11 should work but not 12 or any other two-digit number.
You might use an alternation with an optional - and digits part, or match the ' followed by a second ' and use a capture group with an if clause to match up the "
\b(?<![-'"])(?:1[01]|0?\d)(?:'(?:(?:1[01]|0?\d)\b"?)?|-(?:1[01]|0?\d\b))(?![-'"])
The pattern matches:
\b A word boundary to prevent a partial word match
(?<![-'"]) Negative lookbehind, assert not ' or - or " directly to the left
(?:1[01]|0?\d) Match from 0-9 with optional leading 0 and 10 and 11
(?: Non capture group
' Match literally
(?: Non capture group
(?:1[01]|0?\d)\b
"? Match optional "
)? Close non capture group and make it optional
| Or
- Match literally
(?:1[01]|0?\d\b) Match 0-9 10 or 11 followed by a word boundary
) Close the outer group
(?![-'"]) Negative lookahead, assert not - or ' or " to the right
Regex demo
I want to write regex pattern by def function lets name it is_number(string), which check if string is integer from range -49 to 49. Also number should no contain insignificant zeros.
So i want to pass test:
self.assertTrue(is_number("50"))
self.assertTrue(is_number("-50"))
self.assertTrue(is_number("-9"))
self.assertFalse(is_number("7"))
self.assertFalse(is_number("-200"))
self.assertTrue(is_number("-21"))
self.assertTrue(is_number("18"))
self.assertTrue(is_number("0"))
self.assertTrue(is_number("49"))
self.assertFalse(is_number("100"))
self.assertTrue(is_number("-49"))
I tried something like, but it doesnt work:
def is_number(string):
pattern = r'[-]?\d[1,4]{1,2}*'
return re.search(pattern, string)
You might use
^-?(?:[0-9]|[1-4][0-9])$
That will match
^ Start of string
-? Optional -
(?: Non capturing group
[0-9] Match a digit 0-9
| Or
[1-4][0-9] Match a digit 1-4 and a digit 0-9 to match a range 10 - 49
) Close group
$ End of string
Regex demo
If you also want to match 50 and -50 and 7 should not match you could add 50 to the alternation and match digits 0-6, 8 and 9 using
^-?(?:[0-689]|[1-4][0-9]|50)$
Regex demo
The pattern matches either
double digit numbers with leading 1, 2, 3 or 4 (positive and negative)
or any single digit number (positive and negative)
Regex:
^(-?[1-4]\d|-?\d)$
To fulfill the range of 49 to negative 49 your tests should actually look like this:
self.assertFalse(is_number("50")) # 50 must be assertFalse
self.assertFalse(is_number("-50")) # -50 must be assertFalse
self.assertTrue(is_number("-9"))
self.assertTrue(is_number("7")) # 7 must be assertTrue
self.assertFalse(is_number("-200"))
self.assertTrue(is_number("-21"))
self.assertTrue(is_number("18"))
self.assertTrue(is_number("0"))
self.assertTrue(is_number("49"))
self.assertFalse(is_number("100"))
self.assertTrue(is_number("-49"))
Try this regex pattern,
^[-]?[0-4]?\d$
The first digit must be within the four digits 0,1,2,3 and 4 and the last digit can be any.
pattern = r'^-?[0-4]?\d$'
Try out this regex pattern
As the title, I'm supposed to get some sub-strings from a string which looks like this: "-23/45 + 14/9". What I need to get from that string is the four numbers and the operator in the middle. What has confused me is that how to use only one regular expression pattern to do this. Below is the requirement:
Write a regular expression patt that can be used to extract
(numerator,denominator,operator,numerator,denominator)
from a string containing a fraction, an arithmetic operator, and a fraction. You may
assume there is a space before and after the arithmetic operator and no spaces
surrounding the / character in a fraction. And all fractions will have a numerator and
denominator.
Example:
>>> s = "-23/45 + 14/9"
>>> re.findall(patt,s)
[( "-23","45","+","14","49")]
>>> s = "-23/45 * 14/9"
>>> re.findall(patt,s)
[( "-23","45","*","14","49")]
In general, your code should handle any of the operators +, -, * and /.
Note: the operator module for the two argument function equivalents of the arithmetic
(and other) operators
My problem here is that how to use only one regular expression to do this. I have thought about getting the sub strings contain numbers and stop at any character which is not a number, but this will miss the operator in the middle. Another idea is to include all the operators( + - * /) and stop at white space, but this will make first and last two numbers become together. Can anybody give me a direction how to solve this problem with only one regular expression pattern? Thanks a lot!
Try this regex:
(-?\d+)\s*\/\s*(\d+) *([+*\/-])\s*(-?\d+)\s*\/(\d+)
Click for regex Demo
You can extract the required information from Group 1 to Group 5
Explanation:
(-?\d+) - matches an optional - followed by 1+ occurrences of a digit and capture it in Group 1
\s*\/\s* - matches 0+ occurrences of a whitespace followed by a / followed by 0+ occurrences of a whitespace
(\d+) - matches 1+ occurrences of a digit and capture it in Group 2
* - matches 0+ occurrences of a space
([+*\/-]) - matches one of the operators in +,-,/,* and captures it in Group 3
\s* - matches 0+ occurrences of a whitespace
(-?\d+) - matches an optional - followed by 1+ occurrences of a digit and capture it in Group 4
\s*\/ - matches 0+ occurrences of a whitespace followed by /
(\d+) - matches 1+ occurrences of a digit and capture it in Group 5