I am trying to do a math operation and match a letter of a string:
I got this table:
static final char[] LETTERS = {'T', 'R', 'W', 'A', 'G', 'M', 'Y', 'F', 'P', 'D', 'X','B', 'N', 'J', 'Z', 'S', 'Q', 'V', 'H', 'L', 'C', 'K', 'E'};
And I am getting inputs from keyboard of ID's that are in 012345678X (8 digits + 1 char)
I am trying to make it check for 8digits+1char and got it done like this:
public void check() {
if(input.matches("[0-9]{8}[TRWAGMYFPDXBNJZSQVHLCKE]{1}")){
status = true;}
My problem is that now I need to check the last entered letter matches the table by calculating the numbers of the input % 23. Example of valid inputs:
Now what I did try is this:
int num = Integer.parseInt(input.replaceAll("[^0-9]", ""));
if(input.matches("[0-9]{8}[TRWAGMYFPDXBNJZSQVHLCKE]{1}"))
{
switch(num){
case 0: if(num%23==0){
if(input.charAt(8)==LETTERS[0]){
status = true;
break;
}}
....
case 10: if(num%23==10){
if(input.indexOf(8)==LETTERS[10]){
status = true;
}}
default: status = false;
}
But with no results, any idea where am I going wrong? It's not that I get a compilation or code error, just that every 8digit+1letter input I get it gets accepted. Thank you in advance!
EDIT (PASTED CODE)
import java.util.Scanner;
public class Testing {
static final char[] LETRAS = {'T', 'R', 'W', 'A', 'G', 'M', 'Y', 'F', 'P', 'D', 'X'
,'B', 'N', 'J', 'Z', 'S', 'Q', 'V', 'H', 'L', 'C'
, 'K', 'E'};
String input;
public boolean status = false;
Scanner scanner = new Scanner(System.in);
//Método problema general
public static void main (String[] args) {
Testing programa = new Testing();
programa.inicio();
}
public void inicio() {
Intro();
while (!status){
datosUsuario();
comprobacion();
resultado();
}
}
//Explicar programa
public void Intro() {
System.out.println("¡Hola!\nEste programa pide y comprueba DNI's."
+ "A continuación va a pedir un DNI de forma 8 dígitos y una letra,"
+ "y va a comprobar si es válido.\n"
+ "Ejemplo DNI válido: 24659213Q\n\n");
}
//Métodos primer nivel de decomposición
//Pedir DNI por teclado
public void datosUsuario() {
System.out.print("Escribe DNI: ");
input = scanner.nextLine();
}
//Comprobación DNI
public boolean comprobacion() {
System.out.println("Comprobamos DNI...");
char letra = input.charAt(8);
if(input.matches("[0-9]{8}[TRWAGMYFPDXBNJZSQVHLCKEtrwagmyfpdxbnjzsqvhlcke]{1}"))
{
int numeros = Integer.parseInt(input.replaceAll("[^0-9]", ""));
if(LETRAS[numeros%LETRAS.length] == input.charAt(8)) {
return true;
}
}
return false;
}
//Mostrar resultado
public void resultado() {
if(status&&comprobacion()){
System.out.println("DNI válido!");
}
}
}
I see many problems in your code , first I am not sure why is the switch for? you can simply do it like this
public static boolean isValid(String str) {
if(str.matches("[0-9]{8}[TRWAGMYFPDXBNJZSQVHLCKE]{1}")) {
int num = Integer.parseInt(str.replaceAll("[^0-9]", ""));
if(LETTERS[num%LETTERS.length] == str.charAt(8) ) {
return true;
}
}
return false;
}
String
before matching the regex. If the pattern does not match the String
input.replaceAll("[^0-9]", "")
could return the empty String
; Integer.parseInt
throws an exception in this case.String
contains the number. Using substring
is more efficient than using replaceAll
in this case.switch
.static final char[] LETTERS = {'T', 'R', 'W', 'A', 'G', 'M', 'Y', 'F', 'P', 'D', 'X','B', 'N', 'J', 'Z', 'S', 'Q', 'V', 'H', 'L', 'C', 'K', 'E'};
public static boolean checkInput(String input) {
return input.matches("[0-9]{8}.")
&& LETTERS[Integer.parseInt(input.substring(0, 8)) % LETTERS.length] == input.charAt(8);
}
Try this:
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class RegexTester2 {
static final char[] LETTERS = {'T', 'R', 'W', 'A', 'G', 'M', 'Y', 'F', 'P', 'D', 'X','B', 'N', 'J', 'Z', 'S', 'Q', 'V', 'H', 'L', 'C', 'K', 'E'};
public static boolean isMatch(String input) {
Pattern p = Pattern.compile("^([0-9]{8})([TRWAGMYFPDXBNJZSQVHLCKE])$");
Matcher m = p.matcher(input);
if (m.matches()) {
String strNum = m.group(1);
String lastChar = m.group(2);
int num = Integer.parseInt(strNum);
int idx = num % 23;
return LETTERS[idx] == lastChar.charAt(0);
}
return false;
}
public static void main(String[] args) {
String[] inputs = {
"00000102X",
"24659213Q",
"12345679Z"
};
for (String s : inputs) {
System.out.println("match? " + s + " " + isMatch(s));
}
}
}
Your problem about in your value " num ". You check if ( num % 23 == 10 ) but what is your num ? You need value for " num " you need the get from user or you can give this value yourself. You need this i think good luck.
Do this:
final Pattern pat = Pattern.compile("[0-9]{8}[TRWAGMYFPDXBNJZSQVHLCKE]{1}");
final Matcher finder = pat.matcher(input);
final ArrayList<String> matchList = new ArrayList<String>();
while(finder.find()){
char vchar;
MatchResult mr = finder.toMatchResult();
try {
int vnum = Integer.parseInt(input.substring(mr.start(), mr.end() - 1));
vchar = LETTERS[vnum % 23];
} catch(Exception e){
continue;
}
if(vchar == input.charAt(mr.end() - 1)){
matchList.add(input.substring(mr.start(), mr.end()));
}
}
The input is one string: "00000102X00000102X"
would match twice. You could tweak the code to accept an array of input strings.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.