Short answer: you need this template:
^(?!(?:^[-+]?[0.]+(?:[Ee]|$)))(?!(?:^-))(?:(?:[+-]?)(?=[0123456789.])(?:(?:(?:[0123456789]+)(?:(?:[.])(?:[0123456789]*))?|(?:(?:[.])(?:[0123456789]+))))(?:(?:[Ee])(?:(?:[+-]?)(?:[0123456789]+))|))$
The long answer is in the following program:
#!/usr/bin/perl use strict; use warnings qw<FATAL all>; my $number_rx = qr{ # leading sign, positive or negative (?: [+-] ? ) # mantissa (?= [0123456789.] ) (?: # "N" or "N." or "NN" (?: (?: [0123456789] + ) (?: (?: [.] ) (?: [0123456789] * ) ) ? | # ".N", no leading digits (?: (?: [.] ) (?: [0123456789] + ) ) ) ) # abscissa (?: (?: [Ee] ) (?: (?: [+-] ? ) (?: [0123456789] + ) ) | ) }x; my $negative_rx = qr{ ^ - }x; my $zero_rx = qr{ ^ [-+]? [0.]+ (?: [Ee] | $ ) }x; my $positive_rx = qr{ ^ (?! $zero_rx ) (?! $negative_rx ) $number_rx $ }x; my @test_data = qw{ -2 2 +2 2. -1 1 +1 1. 0 +0 -0 .0 0. 1.3 -3.2 5.13.7 00.00 +00 -00 +0-1 0000. McGillicuddy +365.2425 6.02e23 .0000000000000000000000000000000000000000000000000000000000000000000 .00000000000000000000000000000000000000000000000000000000000000000000000001 .03 0.3 3.0 0e50 0e-50 1e50 1e+50 1e-50 }; for my $n (@test_data) { printf "%s is%sa positive number.\n", $n, $n =~ /$positive_rx/ ? "" : " not"; }
Test results:
-2 is not a positive number. 2 is a positive number. +2 is a positive number. 2. is a positive number. -1 is not a positive number. 1 is a positive number. +1 is a positive number. 1. is a positive number. 0 is not a positive number. +0 is not a positive number. -0 is not a positive number. .0 is not a positive number. 0. is not a positive number. 1.3 is a positive number. -3.2 is not a positive number. 5.13.7 is not a positive number. 00.00 is not a positive number. +00 is not a positive number. -00 is not a positive number. +0-1 is not a positive number. 0000. is not a positive number. McGillicuddy is not a positive number. +365.2425 is a positive number. 6.02e23 is a positive number. .0000000000000000000000000000000000000000000000000000000000000000000 is not a positive number. .00000000000000000000000000000000000000000000000000000000000000000000000001 is a positive number. .03 is a positive number. 0.3 is a positive number. 3.0 is a positive number. 0e50 is not a positive number. 0e-50 is not a positive number. 1e50 is a positive number. 1e+50 is a positive number. 1e-50 is a positive number.
source share