NSRegularExpression Creation/Escaping Error - regex

I want to create the following regular expression with NSRegularExpression:
+(,|.|\n|\s)
One or more occurrences of any of these: comma, full stop (period), new line, whitespace.
I've attempted to create the NSRegularExpression as follows:
NSRegularExpression* regex = [NSRegularExpression regularExpressionWithPattern:#"+(,|.|\\n|\\s)" options:NSRegularExpressionCaseInsensitive error:&error];
The important bit being:
regularExpressionWithPattern:#"+(,|.|\\n|\\s)"
From the class reference, there is this information about escaping/quoting:
Character Expression: \
Description: Quotes the following character. Characters that must be quoted to be treated as literals are * ? + [ ( ) { } ^ $ | \ . /
So, I want the . to be treated as a literal. I've tried the following:
+(,|\.|\\n|\\s)
+(,|\\.|\\n|\\s)
None of the above work; all result in nil for regex with NSCocoaErrorDomain and NSInvalidValue in error.
Can anyone tell me how to create the regular expression that I want?
Thanks.

You might have the quantifier + in the wrong place. In most implementations of Regex the quantifier is applied to a group/character by putting it afterwards, like so:
(,|\\.|\\n|\\s)+

Related

Regular Expression to find string between two characters

I'm trying to create a REGEX to find the string between \ and > in the following input :
\\RANDOM\APPLE\BOB\GEORGE\MIKE\TOM >>\\TEST\TEST2\TEST3\TEST\TEST\JOHN.
Desired Output:TOM
I've been able to create ([^>]+) to isolate the first section of the string before the first > . I just can't seem to figure out how to expand on this and isolate TOM.
Try
\\([^\\>]+?) >>
Regex Demo
In javascript:
let regex = /\\([^\\>]+?) >>/
// Note \\ is required for literal \ in js
let str = "\\\\RANDOM\\APPLE\\BOB\\GEORGE\\MIKE\\TOM >>\\\\TEST\\TEST2\\TEST3\\TEST\\TEST\\JOHN.";
match = str.match(regex);
console.log(match[1]); //TOM
This should works:
[^\\\s>]+(?=\s*>)
Demo:
It will works even if the desired match has one or more > after it and if has one or more whitespaces before >.
I mean: this regex will match TOM from all this strings:
\\RANDOM\APPLE\BOB\GEORGE\MIKE\TOM >\\TEST\TEST2\TEST3\TEST\TEST\JOHN.
\\RANDOM\APPLE\BOB\GEORGE\MIKE\TOM >>\\TEST\TEST2\TEST3\TEST\TEST\JOHN.
\\RANDOM\APPLE\BOB\GEORGE\MIKE\TOM>>\\TEST\TEST2\TEST3\TEST\TEST\JOHN.

Regular expression not working with \ and ]

I have a regex for validating a password which has to be at least 8 chars and must contain letter(upper and lower case) number and a special character from set ^ $ * . [ ] { } ( ) ? - " ! # # % & / \ , > < ' : ; | _ ~ ` .
I face 2 problems, after adding the / to the reg exp its not recognized (other characters are still working OK. If I add the /] as well the expression no longer works (everything is invalid though the pattern seems to be ok in the browser debug mode).
The regex string
static get PASSWORD_VALIDATION_REGEX(): string {
return '(?=.*[a-z])(?=.*[0-9])(?=.*[A-Z])' + // contains lowercase number uppercase
'(?=.*[\-~\$#!%#<>\|\`\\\/\[;:=\+\{\}\.\(\)*^\?&\"\,\'])' + // special
'.{8,}'; // more than allowed char
}
I used the regexp as a form validator and as a match in function
password: ['', {validators: [Validators.required,
Validators.pattern(StringUtils.PASSWORD_VALIDATION_REGEX)
],
updateOn: 'change'
}
]
//....
value.match(StringUtils.PASSWORD_VALIDATION_REGEX)
Tried to use only (?=.*[\\]) for the special chars list, in that case I've received a console error
Invalid regular expression: /^(?=.*[a-z])(?=.*[0-9])(?=.*[A-Z])(?=.*[\]).{8,}$/: Unterminated character class
For '(?=.*[\]])' no console error but the following error is present in the form validation 'pattern'
actualValue: "AsasassasaX000[[][]"
requiredPattern: "^(?=.*[a-z])(?=.*[0-9])(?=.*[A-Z])(?=.*[]]).{8,}$"
The same value and pattern fails on https://regex101.com/
Thanks for your help / suggestions in advance!
You have overescaped your pattern and failed to escape the ] char correctly. In JavaScript regex, ] inside a character class must be escaped.
If you are confused with how to define escapes inside a string literal (and it is rather confusing indeed), you should use a regex literal. One thing to remember about the regex use with Validators.pattern is that the string pattern is anchored by the Angular framework by enclosing the whole pattern with ^ and $, so these anchors must be present when you define the pattern as a regex literal.
Use
static get PASSWORD_VALIDATION_REGEX(): string {
return /^(?=.*[a-z])(?=.*[0-9])(?=.*[A-Z])(?=.*[-~$#!%#<>|`\\\/[\];:=+{}.()*^?&",']).{8,}$/;
}
Note the \] that matches a ] char and \\ to match \ inside [...].

can't get specific query-replace-regexp in emacs to work

I have a block of code as such, and I am trying to modify it with query-replace-regexp in emacs.
fz.D(1,:) = Dcen;
fz.vol(1,:) = (4/3)*pi*((fz.D(1,:)/2).^3);
fz.POC(1,:) = Ac*fz.vol(1,:).^bc;
fz.w(1,:) = cw*fz.D(1,:).^eta;
% size - bin edges
fzl.D(1,:) = Dlim;
I want it to look as so:
fz.D(ind,:) = fz.D(1,:);
fz.vol(ind,:) = fz.vol(1,:);
fz.POC(ind,:) = fz.POC(ind,:);
and so fourth.
I tried to enact this change with the following, but it doesn't seem to work
query-replace-regexp
\(*\)(1,:) = *; -> \1(k,:) = \1(1,:);
But that seems to do nothing.
Any suggestions about how I should fix this?
I don't know emacs, but your regular expression needs to use .* for the 'match any length substring' operation:
query-replace-regexp \(.*\)\((1,:)\) = .*; -> \1(ind,:) = \1\2;
(This also makes use of a second \(\) group to avoid repeating the part of the pattern that you want to repeat in the replacement text)
The reason:
In regular expressions, * is a postfix operator that matches "0 or more of the previous item". When found with no previous item, it matches a plain *. Thus, your expression \(*\)(1,:) = *; matched the exact text *(1,:) = followed by 0 or more spaces followed by ;. You want to use .* to "match anything", as this matches 0 or more . items (where . matches any one non-end-of-line character).

problem in not replaceing minus sign(-) with a blank using regex

I am using this regex expression to replace some characters with ""
I used it as
query=query.replace(/[^a-zA-Z 0-9 * ? : . + - ^ "" _]+/g,'');
But when my query is as +White+Diamond, i get result +White+Diamond, but when query is -White+diamond i am getting White+diamond, it means - is replaced by "" that i don't want.
Please tell me what is the problem.
In regex, - means "from ... to ...", escape your - with a backslash: \-.
What SteeveDroz said:
query=query.replace(/[^a-zA-Z0-9*?:.+\-^"_ ]+/g,'');
I'm assuming you want to exclude spaces as well. If not, remove the final space from the character class.

Regex help. I need ideas for solve the String Calculator kata with Groovy

I'm working on String Calculator code kata with Groovy.
There are a lot of scenarios that solve for achieve the solution:
I have:
//;\n1;2;3
//#\n1#2#3
//+\n1+2+3
//*\n1*2*3
//?\n1?2?3
I want:
1,2,3
My implementation:
String numbers = "//;\n1;2;3"
numbers.find(/\/\/\S[\n]/) { match ->
def delimeter = match[2]
numbers = numbers.minus(match).replaceAll(delimeter, ",")
}
With this solution I solved the first and second expressions, but I don't know how solve the others expressions.
java.util.regex.PatternSyntaxException: Dangling meta character '+' near index 0
The problem is that we must also consider any symbol that match with the sintaxt of regular expressions like +, * or ?
Finally I have the solution:
String numbers = "//+\n1+2+3"
numbers.find(/(?s)\/\/(.*)\n/) { match ->
def delimeter = match[1] // also match[0][2]
numbers = numbers.minus(match[0]).replace(delimeter, ",")
}
An important point (?s):
In dotall mode, the expression . matches any character, including a line terminator. By default this expression does not match line terminators.
Dotall mode can also be enabled via the embedded flag expression (?s)
But really the problem was here: .replace(delimeter, ",")
//(.)\n(\d)\1(\d)\1(\d)
Need to use links.
(.) - math thiw any character, and \1 - math thiw character on it\
For next example you can apply this: //\[(.*?)\]\\n(\d)\1(\d)\1(\d)
It math thiw
//[*]\n12**3
And last: //\[(.*?)\]\[(.*?)\]\\n(\d)\1(\d)\2(\d)
//[*][%%]\n1*2%%3
And finaly:
//\[(.*?)\](?:\[(.*?)\])?\\n(\d)\1(\d)(?:\2|\1)(\d)
I think it's can work ewerythere
P.S : (\d) you can replace what you want. I think you need (\d*)