Updating from ereg to preg_match - preg-match

I read similar titles but I couldn't make it run..
Now, I have a code like this (originally ereg):
if (preg_match("[^0-9]",$qrcode_data_string)){
if (preg_match("[^0-9A-Z \$\*\%\+\-\.\/\:]",$qrcode_data_string)) {
I also tried using / at the beginning and end of rule but didn't work.
Any replies welcome.

With the preg_* functions you need delimiters around the pattern:
if (preg_match("#[^0-9]#", $qrcode_data_string)) {
# ^ ^
From the documentation:
When using the PCRE functions, it is required that the pattern is enclosed by delimiters. A delimiter can be any non-alphanumeric, non-backslash, non-whitespace character.
Often used delimiters are forward slashes (/), hash signs (#) and tildes (~).

Related

How to use inline code with a trailing whitespace?

When I use
``# ``
in my Sphinx documentation I get the following warning:
WARNING: Inline literal start-string without end-string.
Trying
:samp:`# `
leads to
WARNING: Inline interpreted text or phrase reference start-string without end-string.
The problem seems to be the trailing whitespace however I couldn't figure out a way of getting around this problem. Escaping the whitespace with a backslash (\) doesn't help either (for the first example the warning persists and for the second example the whitespace is omitted in the generated docs).
This answer doesn't work because the inline code section interprets the |space| as a literal string.
Experienced with Sphinx 1.6.2.
A workaround is to use a no-break space character (U+00A0) instead of a regular space (U+0020) for the trailing whitespace.
There are several ways to insert a literal no-break space character. See https://en.wikipedia.org/wiki/Non-breaking_space#Keyboard_entry_methods.
Use a "literal" role__ with an escaped space after the intended trailing space::
:literal:`# \ `
__https://docutils.sourceforge.io/docs/ref/rst/roles.html#literal

Ruby Regexp character class with new line, why not match?

I want to use this regex to match any block comment (c-style) in a string.
But why the below does not?
rblockcmt = Regexp.new "/\\*[.\s]*?\\*/" # match block comment
p rblockcmt=~"/* 22/Nov - add fee update */"
==> nil
And in addition to what Sir Swoveland posted, a . matches any character except a newline:
The following metacharacters also behave like character classes:
/./ - Any character except a newline.
https://ruby-doc.org/core-2.3.0/Regexp.html
If you need . to match a newline, you can specify the m flag, e.g. /.*?/m
Options
The end delimiter for a regexp can be followed by one or more
single-letter options which control how the pattern can match.
/pat/i - Ignore case
/pat/m - Treat a newline as a character matched by .
...
https://ruby-doc.org/core-2.3.0/Regexp.html
Because having exceptions/quirks like newline not matching a . can be painful, some people specify the m option for every regex they write.
It appears that you intend [.\s]*? to match any character or a whitespace, zero or more times, lazily. Firstly, whitespaces are characters, so you don't need \s. That simplifies your expression to [.]*?. Secondly, if your intent is to match any character there is no need for a character class, just write .. Thirdly, and most importantly, a period within a character class is simply the character ".".
You want .*? (or [^*]*).

Regex to match "AAAA:AAA" pattern

A string must begin with 3 or 4 letters (not numbers), and a ":" symbol should follow these letters, and after the colon there should be three more characters, like AAA. For example, AAAA:AAA or AAA:AAA.
I`m starting to build this, but regex is so much pain for me, can anyone help me with this?
Here is what I have now:
^[a-zA-Z]{3,4}(:)$
Your regex is almost there: you need to add [a-zA-Z]{3}.
I prefer the [[:alpha:]] POSIX class in Ruby to match letters though.
/[[:alpha:]]/ - Alphabetic character
POSIX bracket expressions are also similar to character classes. They provide a portable alternative to the above, with the added benefit that they encompass non-ASCII characters.
So, here is a possible regex:
\A[[:alpha:]]{3,4}:[[:alpha:]]{3}\z
See demo
The regex matches:
\A - start of string (in RoR, you have to use \A instead of ^, or you will get errors)
[[:alpha:]]{3,4} - 3 or 4 letters
: - literal :
[[:alpha:]]{3} - 3 letters
\z - end of string (in RoR, you have to use \z instead of $, or you will get errors)
To allow just AAA or AAAA, you need to introduce an optional (? quantifier) non-capturing group ((?:...) construction):
\A[[:alpha:]]{3,4}(?::[[:alpha:]]{3})?\z
^^^ ^^
See another demo
Try using this (quotes if regex in your dialect must be passed as a string)
"^[a-zA-Z]{3,4}:[a-zA-Z]{3}$"

How to allow string with letters, numbers, period, hyphen, and underscore?

I am trying to make a regular expression, that allow to create string with the small and big letters + numbers - a-zA-z0-9 and also with the chars: .-_
How do I make such a regex?
The following regex should be what you are looking for (explanation below):
\A[-\w.]*\z
The following character class should match only the characters that you want to allow:
[-a-zA-z0-9_.]
You could shorten this to the following since \w is equivalent to [a-zA-z0-9_]:
[-\w.]
Note that to include a literal - in your character class, it needs to be first character because otherwise it will be interpreted as a range (for example [a-d] is equivalent to [abcd]). The other option is to escape it with a backslash.
Normally . means any character except newlines, and you would need to escape it to match a literal period, but this isn't necessary inside of character classes.
The \A and \z are anchors to the beginning and end of the string, otherwise you would match strings that contain any of the allowed characters, instead of strings that contain only the allowed characters.
The * means zero or more characters, if you want it to require one or more characters change the * to a +.
/\A[\w\-\.]+\z/
\w means alphanumeric (case-insensitive) and "_"
\- means dash
\. means period
\A means beginning (even "stronger" than ^)
\z means end (even "stronger" than $)
for example:
>> 'a-zA-z0-9._' =~ /\A[\w\-\.]+\z/
=> 0 # this means a match
UPDATED thanks phrogz for improvement

count quotes in a string that do not have a backslash before them

Hey I'm trying to use a regex to count the number of quotes in a string that are not preceded by a backslash..
for example the following string:
"\"Some text
"\"Some \"text
The code I have was previously using String#count('"')
obviously this is not good enough
When I count the quotes on both these examples I need the result only to be 1
I have been searching here for similar questions and ive tried using lookbehinds but cannot get them to work in ruby.
I have tried the following regexs on Rubular from this previous question
/[^\\]"/
^"((?<!\\)[^"]+)"
^"([^"]|(?<!\)\\")"
None of them give me the results im after
Maybe a regex is not the way to do that. Maybe a programatic approach is the solution
How about string.count('"') - string.count("\\"")?
result = subject.scan(
/(?: # match either
^ # start-of-string\/line
| # or
\G # the position where the previous match ended
| # or
[^\\] # one non-backslash character
) # then
(\\\\)* # match an even number of backslashes (0 is even, too)
" # match a quote/x)
gives you an array of all quote characters (possibly with a preceding non-quote character) except unescaped ones.
The \G anchor is needed to match successive quotes, and the (\\\\)* makes sure that backslashes are only counted as escaping characters if they occur in odd numbers before the quote (to take Amarghosh's correct caveat into account).

Resources