16

I need a regex which will satisfy both conditions.

It should give me true only when a String contains both A-Z and 0-9.

Here's what I've tried:

if PNo[0].matches("^[A-Z0-9]+$")

It does not work.

informatik01
  • 16,038
  • 10
  • 74
  • 104
Lucky
  • 783
  • 2
  • 10
  • 28
  • I don't see any need to build one regex to accomplish both matches. It would be much quicker (and easier to read) to call `String.matches()` two times and `AND` the two results (see my answer). – jahroy Jul 18 '12 at 02:44

8 Answers8

26

I suspect that the regex below is slowed down by the look-around, but it should work regardless:

.matches("^(?=.*[A-Z])(?=.*[0-9])[A-Z0-9]+$")

The regex asserts that there is an uppercase alphabetical character (?=.*[A-Z]) somewhere in the string, and asserts that there is a digit (?=.*[0-9]) somewhere in the string, and then it checks whether everything is either alphabetical character or digit.

nhahtdh
  • 55,989
  • 15
  • 126
  • 162
23

It easier to write and read if you use two separate regular expressions:

String s  =  "blah-FOO-test-1-2-3";

String numRegex   = ".*[0-9].*";
String alphaRegex = ".*[A-Z].*";

if (s.matches(numRegex) && s.matches(alphaRegex)) {
    System.out.println("Valid: " + input);
}

Better yet, write a method:

public boolean isValid(String s) {
    String n = ".*[0-9].*";
    String a = ".*[A-Z].*";
    return s.matches(n) && s.matches(a);
}
jahroy
  • 22,322
  • 9
  • 59
  • 108
7

A letter may be either before or after the digit, so this expression should work:

(([A-Z].*[0-9])|([0-9].*[A-Z]))

Here is a code example that uses this expression:

Pattern p = Pattern.compile("(([A-Z].*[0-9])|([0-9].*[A-Z]))");
Matcher m = p.matcher("AXD123");
boolean b = m.find();
System.out.println(b);
Sergey Kalinichenko
  • 714,442
  • 84
  • 1,110
  • 1,523
  • I think you should make it clear that this only works if you compile the `Pattern` and use with `Matcher`. It won't work with `.matches()` in `String` class. – nhahtdh Jul 18 '12 at 02:35
  • Your conditions seems to work fine, but i need to check for "_" and "-",, means to say i need only A-Z, 0-9... – Lucky Jul 18 '12 at 02:37
  • @Lucky: You should accept answer which works for you. And clarify your question if your intent doesn't seem to be correctly communicated across. – nhahtdh Jul 18 '12 at 02:40
  • @nhahtdh This is an excellent point, I modified the answer to include a code sample. – Sergey Kalinichenko Jul 18 '12 at 02:42
  • @nhahtdh: this Regex worked for me, just thought of adding some more to it, in case i have a PNo which contains" _ or - " – Lucky Jul 18 '12 at 02:43
  • There are more scenarios. For example, your regex returns `false` for "AXD123A". – Keppil Jul 18 '12 at 09:07
  • @Keppil You're right, I needed to use `find` instead of `matches`. [This is now fixed](http://ideone.com/QkwLE). – Sergey Kalinichenko Jul 18 '12 at 09:40
7

Here is the regex for you

Basics:

Match in the current line of string: .

Match 0 or any amount of any characters: *

Match anything in the current line: .*

Match any character in the set (range) of characters: [start-end]

Match one of the regex from a group: (regex1|regex2|regex3)

Note that the start and end comes from ASCII order and the start must be before end. For example you can do [0-Z], but not [Z-0]. Here is the ASCII chart for your reference enter image description here

Check the string against regex

Simply call yourString.matches(theRegexAsString)

Check if string contains letters:

Check if there is a letter: yourString.matches(".*[a-zA-Z].*")

Check if there is a lower cased letter: yourString.matches(".*[a-z].*")

Check if there is a upper cased letter: yourString.matches(".*[A-Z].*")

Check if string contains numbers:

yourString.matches(".*[0-9].*")

Check if string contains both number and letter:

The simplest way is to match twice with letters and numbers

yourString.matches(".*[a-zA-Z].*") && yourString.matches(".*[0-9].*")

If you prefer to match everything all together, the regex will be something like: Match a string which at someplace has a character and then there is a number afterwards in any position, or the other way around. So your regex will be:

yourString.matches(".*([a-zA-Z].*[0-9]|[0-9].*[a-zA-Z]).*")

Extra regex for your reference:

Check if the string stars with letter

yourString.matches("[a-zA-Z].*")

Check if the string ends with number

yourString.matches(".*[0-9]")

Community
  • 1
  • 1
Fangming
  • 24,551
  • 6
  • 100
  • 90
5

This should solve your problem:

^([A-Z]+[0-9][A-Z0-9]*)|([0-9]+[A-Z][A-Z0-9]*)$

But it's unreadable. I would suggest to first check input with "^[A-Z0-9]+$", then check with "[A-Z]" to ensure it contains at least one letter then check with "[0-9]" to ensure it contains at least one digit. This way you can add new restrictions easily and code will remain readable.

vbezhenar
  • 11,148
  • 9
  • 49
  • 63
1

What about ([A-Z].*[0-9]+)|([0-9].*[A-Z]+) ?

Chip
  • 3,226
  • 23
  • 31
0

Try using (([A-Z]+[0-9])|([0-9]+[A-Z])) .It should solve.

0

use this method:

  private boolean isValid(String str)
  {
    String Regex_combination_of_letters_and_numbers = "^(?=.*[a-zA-Z])(?=.*[0-9])[a-zA-Z0-9]+$";
    String Regex_just_letters = "^(?=.*[a-zA-Z])[a-zA-Z]+$";
    String Regex_just_numbers = "^(?=.*[0-9])[0-9]+$";
    String Regex_just_specialcharachters = "^(?=.*[@#$%^&+=])[@#$%^&+=]+$";
    String Regex_combination_of_letters_and_specialcharachters = "^(?=.*[a-zA-Z])(?=.*[@#$%^&+=])[a-zA-Z@#$%^&+=]+$";
    String Regex_combination_of_numbers_and_specialcharachters = "^(?=.*[0-9])(?=.*[@#$%^&+=])[0-9@#$%^&+=]+$";
    String Regex_combination_of_letters_and_numbers_and_specialcharachters = "^(?=.*[a-zA-Z])(?=.*[0-9])(?=.*[@#$%^&+=])[a-zA-Z0-9@#$%^&+=]+$";

    if(str.matches(Regex_combination_of_letters_and_numbers))
        return true;
    if(str.matches(Regex_just_letters))
        return true;
    if(str.matches(Regex_just_numbers))
        return true;
    if(str.matches(Regex_just_specialcharachters))
        return true;
    if(str.matches(Regex_combination_of_letters_and_specialcharachters))
        return true;
    if(str.matches(Regex_combination_of_numbers_and_specialcharachters))
        return true;
    if(str.matches(Regex_combination_of_letters_and_numbers_and_specialcharachters))
        return true;
    return false;
  }

You can delete some conditions according to your taste

farhad.kargaran
  • 2,233
  • 1
  • 24
  • 30