I need a regex which will test the combination of hexadecimal string. Specifically, the string must have:
Atleast one digit in the range 0 - 9,
At least one digit in the range A - F,
be 12 characters long.
String should not start with 0
Currently I am using var macRegex = new RegExp("^[0-9A-Fa-f]{12}$");. The above regex allow strings like "111111111111" , "000000000000" which i want to avoid . It should allow a string like "944a0c122123"
How can I accomplish this?
To keep the regular expression simple, I'd separate matching the pattern and checking the length:
var re = /^(\d+[a-f]+[\da-f]*|[a-f]+\d+[\da-f]*)$/i;
var s = '011001aFFA77';
console.log(re.test(s) && s.length == 12); // true
var s = '000000000000';
console.log(re.test(s) && s.length == 12); // false
The pattern to match:
one or more digits followed by one or more letters a to f followed by zero or more digits or letters a to f, OR
one or more letters a to f followed by one or more digits followed by zero or more digits or letters a to f
then check the length is 12.
Edit
To meet the new criterion "can't start with 0" (and simplify the expression a bit), the regular expression can be:
var re = /^([1-9]\d*[a-f]+|[a-f]+\d+)[\da-f]*$/i;
var s = '011001aFFA77';
console.log(re.test(s) && s.length == 12); // false
var s = '000000000000';
console.log(re.test(s) && s.length == 12); // false
var s = '011001aFFA77';
console.log(re.test(s) && s.length == 12); // false
var s = 'a11001aFFA77';
console.log(re.test(s) && s.length == 12); // true
var s = '311001aFFA77';
console.log(re.test(s) && s.length == 12); // true
var s = '0000000000a1';
console.log(re.test(s) && s.length == 12); // false
If you don't mind a non RegExp solution this function should do what you want.
function only_hex_len_12(str){
// if the string is the wrong length return false
if(str.length!=12) return false;
var hex_val=parseInt(str,16);
var dec_val=parseInt(str,10);
// If the string is dec return false
if(!isNaN(dec_val)) return false;
// If the string is not hex return false
if(isNaN(hex_val)) return false;
// Otherwise the string is okay so return true
return true;
}
If you want a RegExp solution RobG's answer looks good.
Here is the way I'd go:
/^(?=.*\d)(?=.*[a-f])[1-9a-f][\da-f]{10}[1-9a-f]$/i
Explanation:
/
^ : begining of string
(?=.*\d) : lookahead, at least one digit
(?=.*[a-f]) : lookahead, at least one letter in range a-f
[1-9a-f] : first character, not zero
[\da-f]{10} : ten hex character
[1-9a-f] : last character, not zero
$ : end of string
/i : case insensitive
You can use a set of positive lookaheads to do this.
Here's the regex:
/(?!0).(?=.*\d)(?=.*[a-f])[\da-f]{11}/i
(?!0) Negative lookahead
. Match any character
(?= Positive lookahead
.* Match any character zero to unlimited
\d Match a digit
)
(?= Positive lookahead
.* Match any character zero to unlimited
[a-f] Match a character a-f
)
[\da-f]{11} Match any of the valid characters, 12 times
You can conceptualize this is a logical AND of the expressions in each lookahead (except for the .*).
var regexp = /(?!0).(?=.*\d)(?=.*[a-f])[\da-f]{11}/i;
var test1 = "000000000000";
var test2 = "111111111111";
var test3 = "8179acf0871a";
var test4 = "9abzzzzzzzzz";
var test5 = "0179acf0871a";
console.log(regexp.test(test1));
console.log(regexp.test(test2));
console.log(regexp.test(test3));
console.log(regexp.test(test4));
console.log(regexp.test(test5));
Here's a snippet that demonstrates similar input samples.
Related
I have an alphanumeric string, so I want to mask all the numbers in this string when the count of digits reaches 10. In this example, the digit count has reached the count of 10 two times irrespective of how many space, special character,s or digits are there
For ex:
string 1:- abc23 56 dfg %#34567fhgh0 1234567890 abc345
Output:- abc** ** dfg %#*****fhgh* ********** abc345
It ignores the characters and mask the number when the digit length reaches 10. I want to do this with regex. How can I do that?
You may use something like this:
if ((s.match(/\d/g) || []).length >= 10) {
s = s.replace(/\d/g, '*');
}
This will count the number of digit matches. If there are 10 or more digits, it replaces each one with a '*' character. If you want to only replace the digits if the string contains at least one set of 10 consecutive digits, see the end of the answer.
Here's a complete example:
var arr = ['abc23 56 dfg %#34567fhgh0 1234567890 abc345', 'abc123def'];
for (var i = 0; i < arr.length; i++) {
let s = arr[i];
if ((s.match(/\d/g) || []).length >= 10) {
s = s.replace(/\d/g, '*');
arr[i] = s;
}
console.log(s);
}
Output:
abc** ** dfg %#*****fhgh* ********** abc***
abc123def
If you want the condition to be for 10 consecutive digits, use the following instead:
if (/\d{10}/g.test(s)) {
s = s.replace(/\d/g, '*');
}
You could split() the string into an array, check the length of the string, if it is over 10, then map the mask character where the number was using splice and its key along with Number and isNan.
var str = 'abc23 56 dfg %#34567fhgh0 1234567890'
var str2 = 'abc345'
var str3 = '%#34567fhg7'
var str4 = '1234567890'
const exchange = (str, cap) => {
// split the string and define array
const arr = str.split('')
// condtional to see if string.length is greater than cap
if (str.length > cap) {
// we have a string longer than cap, loop over the array, exclude
// empty spaces and check if value is a number using isNaN, if it is,
// we splice its value using the key with the mask character x
arr.map((char, k) => char !== ' ' ? Number.isNaN(Number(char)) ? null : arr.splice(k, 1, 'x') : null)
// return the value as a string by joining the array values together
return arr.join('')
} else {
// return the string as its length is not more than cap
return str
}
}
console.log(`${exchange(str, 10)}, length = ${str.length}`)
console.log(`${exchange(str2, 10)}, length = ${str2.length}`)
console.log(`${exchange(str3, 10)}, length = ${str3.length}`)
console.log(`${exchange(str4, 10)}, length = ${str4.length}`)
I am creating a project using javascript. I want to implement regex in my project for validation purpose.
Validation is like range of numbers for increasing orders
Here is my requierments.
1-56 --------Pass
15 -----------Pass
1-5-9 --------Fail
asd988 -------Fail
50-49 ------- Fail
I am trying using this
^[0-9]+-[0-9]+$
It is not working for me
Update: A change is user can add multiple values like:
1-56,56,3
You may match a string consisting of a single or two numbers, capture the number(s) and compare them if there are two numbers. Only return false if there is no match or if the first number is less than the second:
const rx = /^(\d+)(?:-(\d+))?$/
const isValid = (string) => {
const m = rx.exec(string);
if (m && !m[2]) {
return true;
} else if (m && parseInt(m[2], 10) > parseInt(m[1], 10)) {
return true;
} else {
return false;
}
}
const strs = ['1-56,56,3', '1-56', '15', '1-5-9', 'asd988', '50-49'];
for (let s of strs) {
console.log( s, s.split(",").every(x => isValid(x)) )
}
The /^(\d+)(?:-(\d+))?$/ regex matches:
^ - start of string
(\d+) - Group 1: one or more digits
(?:-(\d+))? - an optional non-capturing group matching 1 or 0 occurrences of
- - a - char
(\d+) - Group 2: one or more digits
-$ - end of string.
I have a string something like and I want to match just the first '{' of every {{xxxx}} pattern
{{abcd}}{{efg}}{{hij}}
{{abcd}}{{efg}}{{hij}}{
I tried with /(\s|^|.){/g but this pattern matches
{{abcd}}{{efg}}{{hij}}
Can some one guide me in the right direction
You need to use /(^|[^{]){/g (that matches and captures into Group 1 start-of-string or any char other than {, and then matches a {) and check if Group 1 matched at each RegExp#exec iteration. Then, if Group 1 matched, increment the match index:
var re = /(^|[^{]){/g;
var str = "{{abcd}}{{efg}}{{hij}}\n{{abcd}}{{efg}}{{hij}}{";
// 0 8 15 23 31 38 45
var m, indices = [];
while ((m = re.exec(str)) !== null) {
indices.push(m.index + (m[1] ? 1 : 0));
}
console.log(indices);
I'm trying to match a specific URL(http://www.example.me/area/?si=) that allows me to get value from si. si value will be dynamic
http://www.example.me/area/?si=4077765
Get any query string value
function qstr(variable) {
var query = window.location.search.substring(1);
var vars = query.split("&");
for (var i = 0; i < vars.length; i++) {
var pair = vars[i].split("=");
if (pair[0] == variable) {
return pair[1];
}
}
return false;
}
Check Query String Exists
function isset_qstr(field) {
var url = vp_furl();
if (url.indexOf('?' + field + '=') != -1) {
return true;
} else if (url.indexOf('&' + field + '=') != -1) {
return true;
}
return false;
}
I think you need the first function. Vote up if you think its helpful.
Thank you. Good Luck
Assuming that the value of the si key in the query string will always be digits (ie: 0 - 9), try this...
var url = 'http://www.example.me/area/?test=4894&si=4077765&f=fjjjf',
si = url.match(/.*[\?&]si=(\d+)/i)[1];
or a little more generic...
function getQueryStringValue(url, key) {
var regex = new RegExp('.*[\\?&]' + key + '=(\\d+)', 'i');
return url.match(regex)[1];
}
if not digits try this...
/.*[\?&]si=(\w+)/i
Explanation:
.* matches any character (except newline) between 0 and unlimited times
[\?&] match a single character, either ? or &
si= matches the characters si= literally (case insensitive)
(\d+) first capturing group. matches any digit [0-9] between 1 and unlimitted times
i modifier - case insensitive
regex101
Something like that can do the trick I think:
var regex = /http\:\/\/www\.example\.me\/area\/\?si=(\w*)/;
var url = 'http://www.example.me/area/?si=4077765';
var si = url.match(regex)[1]; // si = '4077765'
The first part of the regex is simply your URL "\" is used to escape special characters.
(\d+) is a capturing group that matches all character from a-z, A-Z, 0-9, including the _ (underscore) character from 0 to n iteration.
i want to match a known number(floating point or integer) with a string and finding number of that repeat.
like match 22 in "22.5 98 12 22 322"
how i can do it with regular expression ?
try using this:
if (numbers.indexOf("22") != -1) {
//The number 22 is in the String
}
It's not exactly a regex but why use it when you don't need it?
str.match(/substr/g).length
returns number of occurrences of "substr" in "str". For example:
str = "22.5 98 12 22 322"
num = str.match(/22/g).length
alert(num) // 3
If you want to match integers rather than just substrings, make sure the number is preceded and followed by a space:
str = "22.5 98 12 22 322"
num = str.match(/(^|\s)22($|\s)/g).length
alert(num) // 1
Another option, without regular expressions:
str = "22.5 98 12 22 322"
num = str.split(" ").filter(function(item) {
return Number(item) === 22;
}).length;
If you mean you should find only the numbers that repeat within the same string, you can use something like this:
var test_str = '22 34 55 45345 34 22 555';
var matches = test_str.match(/(\b[0-9]+\b)(?=.+\b\1\b)/g);
// matches contains ["22", "34"], but not "55"
var str = "22.5 98 12 22 322";
var pattern = /22/g;
if (pattern.test(str)) {
// it matches "22", do your logic here...
}
see RegExp and RegExp.test(string) for more
Corrolating integer/floating point numbers from text to regex is
very tricky, since regex has no such concept.
With dynamic input, all the work is constructing the regex programatically.
This example doesn't include scientific notation, but it could.
Pseudo code:
If the input matches this parse regex
/^ (?=.*\d) // must be a digit in the input
([+-]?) // capt (1), optional +/-
[0]* // suck up all leading 0's
(\d*) // capt (2), optional digits, will start with [1-9]
([.]?) // capt (3), optional period
(\d*?) // capt (4), non-greedy optional digits, will start with [1-9]
[0]* // suck up all trailing 0's
$/x
sign = '[+]?';
If !length $2 AND !length $4
sign = '[+-]';
Else
If $1 == '-'
sign = '[-]';
Endif
Endif
whole = '[0]*';
If length $2
whole = '[0]*' + $2;
Endif
decfrac = '[.]? [0]*';
If length $4
$decfrac = '[.] ' + $4 + '[0]*';
Endif
regex = '/(?:^|\s)(?=\S*\d) ' + "$sign $whole $decfrac" + ' (?:\s|$)/x';
Else
// input is not valid
Endif
This is a Perl test case.
The dynamic regex produced has not been tested,
I asume it works but I could be wrong.
#samps = (
'00000.0',
'+.0',
'-.0',
'0.',
'-0.00100',
'1',
'+.1',
'+43.0910',
'22',
'33.e19',
);
for (#samps)
{
print "\nInput: $_\n";
if( /^ (?=.*\d) ([+-]?) [0]*(\d*) ([.]?) (\d*?)[0]*$/x ) # 1,2,3,4
{
my ($sign, $whole, $decfrac);
$sign = '[+]?';
if ( !length $2 && !length $4) {
$sign = '[+-]';
} elsif ($1 eq '-') {
$sign = '[-]';
}
$whole = '[0]*';
if ( length $2) {
$whole = '[0]*'.$2;
}
$decfrac = '[.]? [0]*';
if ( length $4) {
$decfrac = '[.] '.$4.'[0]*';
}
my $regex = '/(?:^|\s)(?=\S*\d) '. "$sign $whole $decfrac" . ' (?:\s|$)/x';
print "Regex: $regex\n";
}
else {
print "**input '$_' is not valid\n";
next;
}
}
Output
Input: 00000.0
Regex: /(?:^|\s)(?=\S*\d) [+-] [0]* [.]? [0]* (?:\s|$)/x
Input: +.0
Regex: /(?:^|\s)(?=\S*\d) [+-] [0]* [.]? [0]* (?:\s|$)/x
Input: -.0
Regex: /(?:^|\s)(?=\S*\d) [+-] [0]* [.]? [0]* (?:\s|$)/x
Input: 0.
Regex: /(?:^|\s)(?=\S*\d) [+-] [0]* [.]? [0]* (?:\s|$)/x
Input: -0.00100
Regex: /(?:^|\s)(?=\S*\d) [-] [0]* [.] 001[0]* (?:\s|$)/x
Input: 1
Regex: /(?:^|\s)(?=\S*\d) [+]? [0]*1 [.]? [0]* (?:\s|$)/x
Input: +.1
Regex: /(?:^|\s)(?=\S*\d) [+]? [0]* [.] 1[0]* (?:\s|$)/x
Input: +43.0910
Regex: /(?:^|\s)(?=\S*\d) [+]? [0]*43 [.] 091[0]* (?:\s|$)/x
Input: 22
Regex: /(?:^|\s)(?=\S*\d) [+]? [0]*22 [.]? [0]* (?:\s|$)/x
Input: 33.e19
**input '33.e19' is not valid
Here's a good tool for you to explore regular expressions :)
http://www.regular-expressions.info/javascriptexample.html
Adopted from the site above:
function demoShowMatchClick() {
var re = new RegExp("(?:^| )+(22(?:$| ))+");
var m = re.exec("22.5 98 12 22 322");
if (m == null) {
alert("No match");
} else {
var s = "Match at position " + m.index + ":\n";
for (i = 0; i < m.length; i++) {
s = s + m[i] + "\n";
}
alert(s);
}
}
This will give you all matches and requires the number to be seperated by beginning or end of string or a whitespace.