Re: Regex for matching dotted numbers
by AppleFritter (Vicar) on Jul 21, 2014 at 10:38 UTC
|
Is it intentional that the last one's only got three parts to it? Anyhow, here's one regex that'll work:
/^(?:[\dx]{1,3}\.){0,3}[\dx]{1,3}$/
This will match between 1 and 4 blocks, each consisting of 1 to 3 digits or x's, separated by periods.
Are you dealing with IP addresses there? If so, you may also be interested in Net::IP::Match, Net::IP::Match::* and Net::IP::CMatch.
EDIT: the OP both edited his post and changed the examples of strings he'd like to match after I posted the above. For reference, this was the original post, in its entirety:
I am trying to have a Regex for a dotted number format as shown below
- 8.1xx.x.x
- 9.0.3xx.x
- 9.0.4xx.x
- . . .
- 9.1xx.x
So any thoughts how I can make a generic regex for matching all these patterns.
| [reply] [d/l] |
|
Basically these are version number for a product. So the series can be as given below
- 8.1.1
- 8.100.1
- 9.0.300.1
- 9.0.301.1
- 9.0.400.1
- 9.0.401.1
- 9.1.0.0
- 9.100.1.0
So I need to make sure that if the version matches above then I need to skip running a particular script else run it.
| [reply] |
|
Please don't make substantial changes to your original posts in a way that makes answers you already received not make sense anymore. Instead, add an addendum to your post to clarify.
Now, that said, what exactly is it you want to do now? You've got a list of version numbers and a version you want to match against them, and you want to run a particular script unless that version is on your list. So why not simply do exactly that in Perl?
foreach (@versions) {
unless($_ eq $version) {
runscript(...);
}
}
Or, more idiomatically:
runscript(...) foreach (grep { $_ ne $version } @versions);
| [reply] [d/l] [select] |
|
|
Re: Regex for matching dotted numbers
by SimonPratt (Friar) on Jul 21, 2014 at 11:59 UTC
|
/^([1-9]\d+|[0-7])(\.\d{1,3}){0,3}$/
Assumptions:
- Version numbers greater than 0 (or 0.something) do not start with 0
- Digit groups are no more than 3 digits long
- Version numbers don't end with a period (.)
| [reply] [d/l] |
Re: Regex for matching dotted numbers
by jellisii2 (Hermit) on Jul 21, 2014 at 11:56 UTC
|
This doesn't necessarily have to be done on a regex...
my @ver = split /\./, $verstring;
And test for whatever you wish there. | [reply] [d/l] |
|
| [reply] |
|
Your supplied test data doesn't suggest this. If it's not 3 or 4 numbers separated by a dot, what is it? If it is separated by a dot, you can check scalar(@ver) to see if it's 3 or 4 numbers, and check $ver[0] to get your major number, and continue from there. You could even use one of the many switch analogs from CPAN to implement switch statements on the version numbers.
| [reply] [d/l] [select] |
Re: Regex for matching dotted numbers
by QM (Parson) on Jul 21, 2014 at 10:42 UTC
|
It helps if you show what you've already tried, and how it behaves. Also tell us what your criteria are, so we can judge which solutions work for you.
Given that I'm lazy today, I'll give a short answer anyway (untested):
my @nums = $dotted_num_string =~ /^(\d+)(?:\.(\d+))*$/;
...which captures the numeric parts in @nums.
If you have some known restriction on how many or how few numeric fields there are, you can use a quantifier:
my @nums = $dotted_num_string =~ /^(\d+)(\.\d+){3,5}$/;
gives 4 to 6 numeric fields.
-QM
--
Quantum Mechanics: The dreams stuff is made of
| [reply] [d/l] [select] |
|
my @nums = $dotted_num_string =~ /^(\d+)(?:\.(\d+))*$/;
...which captures the numeric parts in @nums.
The second capture group above will only return the last substring matched even though it may match many times. A regex solution is possible, but just using split might be preferable. (It's also important to know if the dotted number string is 'alone' or is embedded in a longer string, whether recognition or extraction is intended, etc., none of which is entirely clear to me.)
c:\@Work\Perl\monks>perl -wMstrict -le
"my $dotted_num_string = '1.22.333.4444';
my @nums = $dotted_num_string =~ /^(\d+)(?:\.(\d+))*$/;
printf qq{'$_' } for @nums;
print '';
;;
@nums = $dotted_num_string =~ /^(\d+)(\.\d+){3,5}$/;
printf qq{'$_' } for @nums;
print '';
;;
@nums = $dotted_num_string =~ m{ \G [.]? (\d+) }xmsg;
printf qq{'$_' } for @nums;
"
'1' '4444'
'1' '.4444'
'1' '22' '333' '4444'
| [reply] [d/l] [select] |
|
Yes, agreed. This seems to be a simpler version of your last one:
@nums = $dotted_num_string =~ /(?:(\d+)\.?)/g;
but allows a final trailing dot.
I think your idea of using split, with suitable tests, is probably the best generic solution, barring any further constraints.
-QM
--
Quantum Mechanics: The dreams stuff is made of
| [reply] [d/l] [select] |