2010-09-22 24 views
5

Hola, alguien conoce un reg ex para un formato de fecha en el Reino Unido, p. dd/mm/aaaa.¿Alguien sabe de una expresión de registro para el formato de fecha uk

El dd o mm puede tener 1 caracteres, p. Ej. 1/1/2010, pero el año siempre debe tener 4 caracteres.

Gracias de antemano

+0

qué idioma es esto? – codaddict

+0

@codaddict, las expresiones regulares son de lenguaje neutral en su mayor parte. –

+0

Muchos lenguajes de programación tienen funciones perfectas para analizar la fecha en cualquier formato y ocuparse de la cantidad de días en un mes, años bisiestos, etc. – eumiro

Respuesta

11
^\d{1,2}/\d{1,2}/\d{4}$ 

coincidirán 1/1/2000, 07/05/1999, 99/77/8765, sino también.

Así que si usted quiere hacer la comprobación alguna plausibilidad rudimentaria, es necesario

^(0?[1-9]|[12][0-9]|3[01])/(0?[1-9]|1[012])/\d{4}$ 

Esto todavía coincidirá 31/02/9999, por lo que si se desea capturar los, cada vez es más peludo:

^(?:(?:[12][0-9]|0?[1-9])/0?2|(?:30|[12][0-9]|0?[1-9])/(?:0?[469]|11)|(?:3[01]|[12][0-9]|0?[1-9])/(?:0?[13578]|1[02]))/\d{4}$ 

Pero esto todavía no atrapará años bisiestos. Por lo tanto, la modificación a beast of a regex from regexlib.com:

^(?:(?:(?:(?:31\/(?:0?[13578]|1[02]))|(?:(?:29|30)\/(?:0?[13-9]|1[0-2])))\/(?:1[6-9]|[2-9]\d)\d{2})|(?:29\/0?2\/(?:(?:(1[6-9]|[2-9]\d)(?:0[48]|[2468][048]|[13579][26])|(?:(?:16|[2468][048]|[3579][26])00))))|(?:0?[1-9]|1\d|2[0-8])\/(?:(?:0?[1-9])|(?:1[0-2]))\/(?:(?:1[6-9]|[2-9]\d)\d{2}))$ 

coincidirá con

1/1/2001 
31/5/2010 
29/02/2000 
29/2/2400 
23/5/1671 
01/1/9000 

y fallar

31/2/2000 
31/6/1800 
12/12/90 
29/2/2100 
33/3/3333 

Con todo, las expresiones regulares pueden ser capaces de coincidir con las fechas; validarlos no es su fuerte, pero si son todo lo que puedes usar, ciertamente es posible. Pero se ve horrible :)

+2

Por lo general, es mejor, una vez que haya encontrado una coincidencia probable, incluirla en una variable de escriba la fecha (en cualquier plataforma) y deje que la plataforma se preocupe por las reglas del año bisiesto, etc. –

+0

El primer 0 no es opcional, sufíchelo con un '?' –

+1

O manténgalo simple, o busque en la web una expresión que maneja todo, incluidos los años bisiestos. Realmente no tiene sentido hacer una expresión más complicada si todavía no puede manejar todos los casos. – Guffa

1
\b(0?[1-9]|[12][0-9]|3[01])[/](0?[1-9]|1[012])[/](19|20)?[0-9]{2}\b 

partido:

  • 1/1/2010
  • 01/01/2010

pero también las fechas no válidas como 31ra de febrero de

+0

Creo que coincidir los días correctos en un mes es inútil cuando no coincide con febrero y años bisiestos;) Además eso, es una diferencia entre hacer coincidir la forma y hacer coincidir los valores. –

0

^\d{1,2}/\d{1,2}/\d{4}$

En llaves hay recuento de char mínimo y máximo. \d significa dígito, ^ inicio y $ fin de cadena.

4

Regex no es la herramienta adecuada para este trabajo.

Es muy difícil (pero posible) obtener la expresión regular para que coincida con una fecha válida de . Cosas como asegurar que Feb tenga 29 días en año bisiesto y no es fácil hacer cosas en regex.

En su lugar, verifique si su biblioteca de idiomas proporciona alguna función para validar las fechas.

PHP tiene una tal función llamada checkdate:

bool checkdate (int $month , int $day , int $year) 
0
\b(0[1-9]|[12][0-9]|3[01])[- /.](0[1-9]|1[012])[- /.](19|20)\d\d 

Esta costumbre validar la fecha, pero se puede comprobar si el formato

0

me encontré con los requisitos similares. Aquí está la expresión regular completa junto con la validación del año bisiesto. Formato: dd/mm/aaaa

(3 [01] | [12] \ d | 0 [1-9])/(0 [13578] | 10 | 12)/((?! 0000) \ d {4}) | (30 | [12] \ d | 0 [1-9])/(0 [469] | 11)/((?! 0000) \ d {4}) | (2 [0- 8] | [01] \ d | 0 [1-9])/(02)/((?! 0000) \ d {4}) | 29/(02)/(1600 | 2000 | 2400 | 2800 | 00) | 29/(02)/(\ d \ d) (0 [48] | [2468] [048] | [13579] [26])

Se puede modificar fácilmente al formato de EE. UU. U otros formatos de la UE.

Editado:

(3 [01] | [12] \ d | 0 [1-9])/(0 [13578] | 10 | 12)/((?! 0000) \ d {4}) | (30 | [12] \ d | 0 [1-9])/(0 [469] | 11)/((?! 0000) \ d {4}) | (2 [0- 8] | [01] \ d | 0 [1-9])/(02)/((?! 0000) \ d {4}) | 29/(02)/(1600 | 2000 | 2400 | 2800 | 00) | 29/(02)/(\ d \ d) (0 [48] | [2468] [048] | [13579] [26])

+0

falla el 29/02/2000.los años del siglo 1600 y 2000 son años bisiestos, pero los años del siglo 1700, 1800 y 1900 no lo fueron – Leo

+0

lo arreglaron: eliminar el espacio antes del 29. He editado el original. – Leo

0

Hay dos cosas que desea hacer, que en mi la vista se considera mejor por separado

1) Desea asegurarse de que la fecha sea real y real. Por ejemplo, el 2019-02-29 no es una fecha real, mientras que 2020-02-29 es una fecha real porque 2020 es un año bisiesto

2) Desea verificar que la fecha esté en el formato correcto (tan dd/mm/aaaa)

El segundo punto se puede hacer con bastante facilidad con un simple RegEx, muchos ejemplos de eso.

Para complicar las cosas, si le preguntas a Firefox si 2019-02-29 es una fecha real, devolverá NaN, que es lo que esperas.

Chrome, por otra parte, se dice que es una cita de verdad y le devolverá el 1 de marzo 2019 - que validará

Chrome, será también aceptar un número de un solo dígito como una fecha adecuada también para algunos Por alguna extraña razón, aliméntelo "2" y le dará la fecha completa del 2001 - que validará

El primer paso es crear una función que intente descifrar una fecha (sin importar el formato) y funciona -browser para devolver un valor booleano que indique si la fecha es válida o no

function validatableDate(value) 
{ 
    Date.prototype.isValid = function() 
    { // An invalid date object returns NaN for getTime() and NaN is the only 
     // object not strictly equal to itself. 
     return this.getTime() === this.getTime(); 
    }; 
    minTwoDigits = function(n) 
    { //pads any digit less than 10 with a leading 0 
     return (parseInt(n) < 10 ? '0' : '') + parseInt(n); 
    } 
    var valid_date = false; 
    var iso_array = null; 
    // check if there are date dividers (gets around chrome allowing single digit numbers) 
    if ((value.indexOf('/') != -1) || (value.indexOf('-') != -1)) { //if we're dealing with - dividers we'll do some pre-processing and swap them out for/
     if (value.indexOf('-') != -1) { 
      dash_parts = value.split('-'); 
      value = dash_parts.join("/"); 
      //if we have a leading year, we'll put it at the end and work things out from there 
      if (dash_parts[0].length > 2) { 
       value = dash_parts[1] + '/' + dash_parts[2] + '/' + dash_parts[0]; 
      } 
     } 

     parts = value.split('/'); 
     if (parts[0] > 12) { //convert to ISO from UK dd/mm/yyyy format 
      iso_array = [parts[2], minTwoDigits(parts[1]), minTwoDigits(parts[0])] 
     } else if (parts[1] > 12) { //convert to ISO from American mm/dd/yyyy format             
      iso_array = [parts[2], minTwoDigits(parts[0]), minTwoDigits(parts[1])] 
     } else //if a date is valid in either UK or US (e.g. 12/12/2017 , 10/10/2017) then we don't particularly care what format it is in - it's valid regardless 
     { 
      iso_array = [parts[2], minTwoDigits(parts[0]), minTwoDigits(parts[1])] 
     } 

     if (Array.isArray(iso_array)) { 
      value = iso_array.join("-"); 
      var d = new Date(value + 'T00:00:01Z'); 
      if (d.isValid()) //test if it is a valid date (there are issues with this in Chrome with Feb) 
      { 
       valid_date = true; 
      } 
      //if the month is Feb we need to do another step to cope with Chrome peculiarities 
      if (parseInt(iso_array[1]) == 2) { 
       month_info = new Date(iso_array[0], iso_array[1], 0); 
       //if the day inputed is larger than the last day of the February in that year 
       if (iso_array[2] > month_info.getDate()) { 
        valid_date = false; 
       } 
      } 
     } 
    } 
    return valid_date; 
} 

que puede ser comprimido hasta

function validatableDate(t) { 
    Date.prototype.isValid = function() { 
     return this.getTime() === this.getTime() 
    }, minTwoDigits = function (t) { 
     return (parseInt(t) < 10 ? "0" : "") + parseInt(t) 
    }; 
    var a = !1, 
     i = null; 
    return -1 == t.indexOf("/") && -1 == t.indexOf("-") || (-1 != t.indexOf("-") && (dash_parts = t.split("-"), t = dash_parts.join("/"), dash_parts[0].length > 2 && (t = dash_parts[1] + "/" + dash_parts[2] + "/" + dash_parts[0])), parts = t.split("/"), i = parts[0] > 12 ? [parts[2], minTwoDigits(parts[1]), minTwoDigits(parts[0])] : (parts[1], [parts[2], minTwoDigits(parts[0]), minTwoDigits(parts[1])]), Array.isArray(i) && (t = i.join("-"), new Date(t + "T00:00:01Z").isValid() && (a = !0), 2 == parseInt(i[1]) && (month_info = new Date(i[0], i[1], 0), i[2] > month_info.getDate() && (a = !1)))), a 
} 

que le consigue una prueba de cross-browser en cuanto a si la fecha se puede validar o no, y que va a leer & descifrar las fechas en formatos

  • aaaa -mm-dd
  • dd-mm-aaaa
  • mm-dd-aaaa
  • dd/mm/aaaa
  • mm/dd/aaaa

Una vez que hayas confirmado que la fecha es verdadera, puedes probar el formato con una expresión regular. Así que para el Reino Unido dd/mm/aa

function dateUK(value) { 
    valid_uk_date=false; 
    valid_date=validatableDate(value); 
    if(valid_date && value.match(/^(0?[1-9]|[12][0-9]|3[01])[\/](0?[1-9]|1[012])[\/]\d{4}$/)) 
    { valid_uk_date=true; 
    } 
    return valid_uk_date;    
} 

A continuación, sabe que la fecha es real y que es en el formato correcto.

Para el formato aaaa-mm-dd, que haría:

function dateISO(value) { 
    valid_iso_date=false; 
    valid_date=validatableDate(value); 
    if(valid_date && value.match(/^\d{4}[\/\-]\d{1,2}[\/\-]\d{1,2}$/)) 
    { valid_iso_date=true; 
    } 
    return valid_iso_date;    
} 

Depende de lo profundo que desea ser, por supuesto, para una verificación aproximada del formato de la cordura una expresión regular puede ser suficiente para sus propósitos . Sin embargo, si desea probar si la fecha es real y si el formato es válido, entonces esto se espera ayude a punto de que en el camino

Gracias

Cuestiones relacionadas