2010-11-26 7 views
9

Estoy construyendo una aplicación .Net y necesito para despojar a cualquier carácter no decimal de una cadena (excluyendo la primera ''). Básicamente estoy limpiando la entrada del usuario para forzar un resultado de número real.Encuentra todos, pero la primera vez que aparece un personaje con Regex

Hasta ahora he estado utilizando herramientas RegEx en línea para tratar de lograr esto en una sola pasada, pero no voy a llegar muy lejos.

deseo de lograr esto:

asd123.asd123.123.123 = 123.123123123 

Por desgracia, sólo las he arreglado para llegar a la etapa en la que

asd123.asd123.123.123 = 123.123.123.123 

mediante el uso de este código.

System.Text.RegularExpressions.Regex.Replace(str, "[^\.|\d]*", "") 

Pero estoy atascado tratando de eliminar todo menos el primer punto decimal.

se puede hacer esto en una sola pasada?
¿Hay una manera mejor ™?

+0

's/[.]/\ X {DEADBEEF} /; s/[^. \ d \ x {DEADBEEF}] // g; s/\ x {DEADBEEF} /./; ' – tchrist

Respuesta

6

Esto se puede hacer en una sola expresión regular, al menos en .NET que soporta repetición infinita dentro lookbehind assertions:

resultString = Regex.Replace(subjectString, @"(?<!^[^.]*)\.|[^\d.]", ""); 

Explicación:

(?<!^[^.]*) # Either match (as long as there is at least one dot before it) 
\.   # a dot 
|   # or 
[^\d.]  # any characters except digits or dots. 

(?<!^[^.]*) significa: Assert que es imposible hacer coincidir una cadena que comienza al principio de la cadena de entrada y consiste únicamente en personajes que no sean puntos Esta condición es verdadera para todos los puntos después de la primera.

+1

Gracias, este ejemplo me ha enseñado cosas que nunca supe acerca de la expresión regular. – Mike

+0

gracias, ¡aprendí algo nuevo también! ¡No pude entender el ejemplo hasta que leí el enlace para ver las afirmaciones subyacentes!esto me ayudó también! –

0

En primer lugar, la expresión regular que está utilizando actualmente deja ningún | caracteres intactos Sólo es necesario [^.\d]* desde . tiene ningún significado especial en []

Después de esta sustitución, que podría intentar algo como esto:

Replace(str, "([\d]+\.[\d]+)[^\d].*", "\1"); 

Pero usted sólo necesita esto si hay un . en absoluto en el número.

Espero que esto ayude.

+0

Gracias por arreglar la primera parte. Según http://regexpal.com/, ¿su segunda expresión regular coincidiría con 123.123.123.123? ¿Es ese el efecto deseado? No he visto "\ 1" usado antes. – Mike

+0

Hmm, la segunda expresión regular debe coincidir con todo ello, a continuación, reemplazarlo con \ 1 (que debería ser el primer sub-patrón, la parte en '()') dejando sólo 123.123 - a menos .NET utiliza un sistema de expresiones regulares diferente de lo que soy ¡Acostumbrado a! –

2

Creo que va a ser hecho mejor sin expresiones regulares.

string str = "asd123.asd123.123.123"; 
StringBuilder sb = new StringBuilder(); 
bool dotFound = false; 
foreach (var character in str) 
{ 
    if (Char.IsDigit(character)) 
     sb.Append(character); 
    else if (character == '.') 
     if (!dotFound) 
     { 
      dotFound = true; 
      sb.Append(character); 
     } 
} 
Console.WriteLine(sb.ToString()); 
+0

Gracias, aprecio esta respuesta. Ni siquiera se me había pasado por la mente intentar este tipo de lógica. Ojalá pudiera aceptar 2 respuestas. – Mike

Cuestiones relacionadas