2010-05-12 16 views
12

Estoy tratando de escribir una expresión regular que especifique que el texto debe comenzar con una letra, cada carácter debe ser una letra, número o guión bajo, no debería haber 2 guiones bajos consecutivos y debería terminar con una letra o número. En este momento, lo único que tengo es ^[a-zA-Z]\w[a-zA-Z1-9_], pero parece que no funciona bien, ya que solo coincide con 3 caracteres y permite subrayados repetidos. Tampoco sé cómo especificar los requisitos para el último personaje.Expresión regular - comenzando y terminando con una letra, aceptando solo letras, números y _

+0

Qué idioma dialecto/expresiones regulares está usando? –

+0

¿Por qué su última clase de caracteres no incluye ceros? – SilentGhost

+0

No estoy seguro. Lo estoy probando en el bloc de notas ++ sin embargo. En cuanto a no incluir cero, eso es un error. – jreid9001

Respuesta

6
^[A-Za-z][A-Za-z0-9]*(?:_[A-Za-z0-9]+)*$ 
4

he aquí una solución utilizando una búsqueda negativa hacia delante (no se admite en todos los sistemas de expresiones regulares):

^[a-zA-Z](((?!__)[a-zA-Z0-9_])*[a-zA-Z0-9])?$ 

prueba de que funciona como se esperaba:

import re 
tests = [ 
    ('a', True), 
    ('_', False), 
    ('zz', True), 
    ('a0', True), 
    ('A_', False), 
    ('a0_b', True), 
    ('a__b', False), 
    ('a_1_c', True), 
] 

regex = '^[a-zA-Z](((?!__)[a-zA-Z0-9_])*[a-zA-Z0-9])?$' 
for test in tests: 
    is_match = re.match(regex, test[0]) is not None 
    if is_match != test[1]: 
     print "fail: " + test[0] 
0

viendo cómo las reglas son bastante complicado, sugeriría lo siguiente:

/^[a-z](\w*)[a-z0-9]$/i 

coinciden con toda la cadena y la captura intermedia e personajes. Entonces, o con las funciones de cadena o la siguiente expresión regular:

/__/ 

de verificación si la parte capturada tiene dos guiones en una fila. Por ejemplo en Python que se vería así:

>>> import re 
>>> def valid(s): 
    match = re.match(r'^[a-z](\w*)[a-z0-9]$', s, re.I) 
    if match is not None: 
     return match.group(1).count('__') == 0 
    return False 
35

Voy a tomar una puñalada en ella:

/^[a-z](?:_?[a-z0-9]+)*$/i 

Explicación:

/ 
^   # match beginning of string 
[a-z]  # match a letter for the first char 
(?:   # start non-capture group 
    _?   # match 0 or 1 '_' 
    [a-z0-9]+ # match a letter or number, 1 or more times 
)*   # end non-capture group, match whole group 0 or more times 
$   # match end of string 
/i   # case insensitive flag 

El grupo no se hace cargo de la captura a) no permite dos _ (fuerza al menos una letra o número por grupo) yb) solo permite que el último carácter sea una letra o número.

Algunas cadenas de prueba:

"a": match 
"_": fail 
"zz": match 
"a0": match 
"A_": fail 
"a0_b": match 
"a__b": fail 
"a_1_c": match 
+0

Esto es más útil que la respuesta aceptada, ya que explica qué significa cada carácter de agrupación/reserva. Gracias por los detalles ya que la expresión regular a menudo es un idioma extraño. –

Cuestiones relacionadas