2

Initially, I had a requirement that I should check whether a given string follows following two patterns.

  • "^(.{1,5})?$" --It is meant to check whether the string is of length up to 5 characters
  • "[!-~]|([!-~][ -~]*[!-~])" -It is meant to signify that String does not start or end with white spaces.

Earlier we were to give two different messages when the string would not match any, so I handled like below :

    Pattern pattern1 = Pattern.compile("^(.{1,5})?$");
    Pattern pattern2 = Pattern.compile("[!-~]|([!-~][ -~]*[!-~])");
    Matcher matcher1=pattern1.matcher(" verify");
    Matcher matcher2 = pattern2.matcher("verify");
    System.out.println("Message1 - " + matcher1.matches());
    System.out.println("Message2 - " + matcher2.matches());

But now the requirement is that we need to : --We need to club both the above patterns BUT

--Also include that the string can contain the following characters $, #,@ other than letters, number

--And give one single message.

I looked on many similiar questions asked like: regex for no whitespace at the begining and at the end but allow in the middle and https://regex101.com/ to make a single regex like :

Pattern pattern3=Pattern.compile(
  "^[^\\\s][[-a-zA-Z0-9-()@#$]+(\\\s+[-a-zA-Z0-9-()@#$]+)][^\\\s]{1,50}$");

But the regex is not working correctly. If I provide a string with a character other than mentioned in the regex like '%' it should have failed but it passed.

I am trying to figure out that what is problem in the above regex or any new regex which can fulfil the need.

@edit to be more clear: Valid input : "Hell@"

Invalid input : " Hell" (have whitepace @beginning)

Invalid input : "Hell%" conatins not required char '%'

Deep
  • 929
  • 2
  • 16
  • 32
  • Why must this be done with regular expressions only? You can check string length is between 1 and 5 by just calling length() and you can test Character.isWhitespace(string.charAt(0)) and at length()-1 for the last char. – emilles Jan 19 '19 at 05:51
  • 1
    @anubhava added more clear inputs – Deep Jan 19 '19 at 05:56
  • @emilles we have a certain framework which uses a regex and do all stuff, so we don't have to use java methods because the requirement like length would vary for every pattern and then we will have to write code again and agian – Deep Jan 19 '19 at 05:58
  • @RamandeepSingh: `Hello@` has 6 characters but you mentioned only up to 5 are allowed? – anubhava Jan 19 '19 at 06:02
  • That's fine, but it's confusing that your example is in Java. You could have given a pure regex example along with sample inputs. – emilles Jan 19 '19 at 06:04
  • @anubhava yes thanks, i corrected it – Deep Jan 19 '19 at 06:34

2 Answers2

2

You may use this regex:

^(?!\s)[a-zA-Z\d$#@ ]{1,5}(?<!\s)$

RegEx Demo

RegEx Details:

  • ^: Start
  • (?!\s): Negative lookahead, don't allow space at start
  • [a-zA-Z\d$#@ ]{1,5}: Allow these character between 1 to 5 in length
  • (?<!\s): Negative lookbehind, don't allow space before end
  • $: End
anubhava
  • 761,203
  • 64
  • 569
  • 643
  • 1
    Thanks @anubhava it worked perfectly, in fact, I needed some more customization and I was able to do it https://regex101.com/r/3oMrRn/1 – Deep Jan 19 '19 at 08:42
  • 1
    You can shorten your regex to this: `/^(?!\s)[][\w!"#$%&'*+.:=@,\/;<>?#@^()\`{}~ -]{1,5}(?<!\s)$/` – anubhava Jan 19 '19 at 09:10
0

Here is a pattern which should meet your two requirements:

^\S(?:.{0,3}\S)?$

This says to match:

\S        an initial non whitespace character
(
    .{0,3}    zero to three of any character (whitespace or non whitespace)
    \S        a mandatory ending whitespace character
)?        the entire quantity optional

Demo

Tim Biegeleisen
  • 502,043
  • 27
  • 286
  • 360