2012-10-11 12 views
13

Qual è il modo più rapido per verificare che una stringa contenga solo caratteri alfanumerici.Il modo più veloce per verificare una stringa è alfanumerico in Java

Ho un codice che masticherà molta CPU e mi chiedo se ci sarà un modo più rapido di usare le espressioni regolari precompilate.

AGGIORNAMENTO: Così tanti voti negativi, cura di spiegare? StackOverflow non dovrebbe essere usato per discutere quale algoritmo usare per realizzare un'attività potrebbe essere più veloce?

+1

Noi non possiamo dirvi come scrivere codice più veloce di qualcosa che non ci mostrerà ... –

+1

precoce ottimizzazione? Indice di riferimento? Profiling? –

+1

@StephenC Non c'è codice da mostrare, mi sto chiedendo quale sia la via _best_. – Jacob

risposta

16

Ho scritto i test che verificano la risposta "corretta". Test eseguiti su una macchina quad core OSX10.8 con Java 1.6

È interessante notare che l'uso di espressioni regolari risulta essere circa 5-10 volte più lento rispetto all'iterazione manuale di una stringa. Inoltre la funzione isAlphanumeric2() è leggermente più veloce di isAlphanumeric().

public class QuickTest extends TestCase { 

    private final int reps = 1000000; 

    public void testRegexp() { 
     for(int i = 0; i < reps; i++) 
      ("ab4r3rgf"+i).matches("[a-zA-Z0-9]"); 
    } 

public void testIsAlphanumeric() { 
    for(int i = 0; i < reps; i++) 
     isAlphanumeric("ab4r3rgf"+i); 
} 

public void testIsAlphanumeric2() { 
    for(int i = 0; i < reps; i++) 
     isAlphanumeric2("ab4r3rgf"+i); 
} 

    public boolean isAlphanumeric(String str) { 
     for (int i=0; i<str.length(); i++) { 
      char c = str.charAt(i); 
      if (!Character.isDigit(c) && !Character.isLetter(c)) 
       return false; 
     } 

     return true; 
    } 

    public boolean isAlphanumeric2(String str) { 
     for (int i=0; i<str.length(); i++) { 
      char c = str.charAt(i); 
      if (c < 0x30 || (c >= 0x3a && c <= 0x40) || (c > 0x5a && c <= 0x60) || c > 0x7a) 
       return false; 
     } 
     return true; 
    } 

} 
24

Usa String.matches(), come:

String myString = "qwerty123456"; 
System.out.println(myString.matches("[A-Za-z0-9]+")); 

Questo non può essere il possibile approccio "più veloce" assoluto. Ma in generale non ha molto senso cercare di competere con le persone che scrivono la "libreria standard" della lingua in termini di prestazioni.

+0

Sì. C# ha una funzione standard per questo. Sembra che Java no. – Jacob

2

Una regex sarà probabilmente abbastanza efficiente, poiché è necessario specificare intervalli: [0-9a-zA-Z]. Supponendo che il codice di implementazione per le regex sia efficiente, ciò richiederebbe semplicemente un confronto limite superiore e inferiore per ogni intervallo. Ecco fondamentalmente ciò che una regex compilato dovrebbe fare:

boolean isAlphanumeric(String str) { 
    for (int i=0; i<str.length(); i++) { 
     char c = str.charAt(i); 
     if (c < 0x30 || (c >= 0x3a && c <= 0x40) || (c > 0x5a && c <= 0x60) || c > 0x7a) 
      return false; 
    } 

    return true; 
} 

Io non vedo come il codice potrebbe essere più efficiente di questo, perché dovrà essere controllato ogni personaggio, e il confronto non poteva davvero essere più semplice .

+1

Probabilmente sarà tra questo e 'String.matches()'. Speravo che qualcuno lo avesse già fatto prima. Sembra che dovrò scrivere il test da solo (: – Jacob

Problemi correlati