2010-09-23 17 views

Respuesta

26
str.split("(?=[:;])") 

Esto le dará la matriz deseada, solo con un primer elemento vacío. Y:

str.split("(?=\\b[:;])") 

Esto dará la matriz sin el primer elemento vacío.

  • La clave aquí es el (?=X) que es un ancho de cero búsqueda positiva hacia delante (constructo no captura) (véase regex pattern docs).
  • [:;] significa "bien; o:"
  • \b es límite de palabra - que está ahí con el fin de no considerar la primera : como delimitador (ya que es el comienzo de la secuencia)
+0

'(? = X)' es "búsqueda positiva de ancho cero", el grupo que no captura es '(?: X)'. Esto no funcionaría correctamente con el grupo que no capturó ... –

+0

@Carlos Heuberger ¿podría explicar más? Realmente funciona de esta manera (lo probé), pero podría haber perdido algo – Bozho

+1

funciona, pero la secuencia '(? = X)' no se llama "grupo no capturante", o al menos no el simple "grupo no capturante" . Se llama "búsqueda positiva de ancho cero". El "grupo que no captura" es '(?: X)'. (perdón por mi mal inglés) –

4

para mantener a los separadores, se puede utilizar un StringTokenizer:

new StringTokenizer(":alpha;beta:gamma;delta", ":;", true) 

Eso daría como los separadores de fichas.

Para tenerlos como parte de sus tokens, puede usar String#split con lookahead.

+3

"StringTokenizer es una clase de legado" – Bozho

+3

@Bozho Es cierto, pero creo que este caso en particular de mantener los delimitadores no está cubierto muy bien por cuerdas #split, que requiere un conocimiento detallado de expresiones regulares para obtener eso. –

+0

cierto, es un poco más claro con StringTokenizer, ya que tiene la opción deseada como un parámetro booleano. +1, el punto de ser legado sigue siendo válido. – Bozho

-1

Suponiendo que usted solo tiene un conjunto finito de separadores antes de las palabras en su cadena (ej.;,: etc.) puede usar la siguiente técnica. (disculpas por los errores de sintaxis, pero ha sido un tiempo desde que utiliza Java)

String toSplit = ":alpha;beta:gamma;delta " 
toSplit = toSplit.replace(":", "~:") 
toSplit = toSplit.replace(";", "~;") 
//repeat for all you possible seperators 
String[] splitStrings = toSplit.split("~") 
+0

esto es más simple. – Joset

+0

1. Es incorrecto ya que devuelve un 0º elemento vacío. 2. Aumenta la posibilidad de error debido a duplicaciones (es decir, ":" debe estar emparejado con "~:") 3. ¿Qué sucede si se utiliza el delimitador especial "~" en una de las subcadenas? –

+0

@Tony, seleccioné "~" como ejemplo pero se podría usar cualquier otro delimitador único que fuera apropiado para el conjunto de datos disponible. No veo muy bien cómo aumenta la posibilidad de error. Quizás puedas aclarar ese punto. Admito que deja un elemento 0 vacío que es un error de este enfoque, pero quería presentar otra opción que no dependiera de regex – chillysapien

1

Usted puede hacer esto mediante el simple uso de patrones y la clase de coincidencias en regx java.

public static String[] mysplit(String text) 
    { 
    List<String> s = new ArrayList<String>(); 
    Matcher m = Pattern.compile("(:|;)\\w+").matcher(text); 
    while(m.find()) { 
    s.add(m.group()); 
    } 
    return s.toArray(new String[s.size()]); 
    } 
+0

Una vez que el genio regexp está fuera de la botella, prefiero la solución de Bozho. –

+0

Sí ... estoy de acuerdo ... arriba era solo una manera alternativa de hacerlo :) – Favonius

1
/** 
* @param list an empty String list. used for internal purpose. 
* @param str String which has to be processed. 
* @return Splited String Array with delimiters. 
*/ 
public String[] split(ArrayList<String> list, String str){ 
    for(int i = str.length()-1 ; i >=0 ; i--){ 
    if(!Character.isLetterOrDigit((str.charAt(i)))) { 
     list.add(str.substring(i, str.length())); 
     split(list,str.substring(0,i)); 
     break; 
    } 
    } 
    return list.toArray(new String[list.size()]); 
} 
+1

¡Esto es solo una forma más! para quienes no saben sobre expresiones regulares como yo :) –

0

Esto debería funcionar con Java 1.5 (Pattern.quote se introdujo en Java 1.5).

// Split the string on delimiter, but don't delete the delimiter 
private String[] splitStringOnDelimiter(String text, String delimiter, String safeSequence){ 
    // A temporary delimiter must be added as Java split method deletes the delimiter 

    // for safeSequence use something that doesn't occur in your texts 
    text=text.replaceAll(Pattern.quote(delimiter), safeSequence+delimiter); 
    return text.split(Pattern.quote(safeSequence)); 
} 

Si primer elemento es el problema:

private String[] splitStringOnDelimiter(String text, String delimiter, String safeSequence){ 
    text=text.replaceAll(Pattern.quote(delimiter), safeSequence+delimiter); 
    String[] tempArray = text.split(Pattern.quote(safeSequence)); 
    String[] returnArray = new String[tempArray.length-1]; 
    System.arraycopy(tempArray, 1, returnArray, 0, returnArray.length); 
    return returnArray; 
} 

P. ej, Aquí "a" es el delimitador:

splitStringOnDelimiter("-asd-asd-g----10-9asdas jadd", "a", "<>") 

Se obtiene lo siguiente:

1.: - 
2.: asd- 
3.: asd-g----10-9 
4.: asd 
5.: as j 
6.: add 

Si, de hecho, quiere esto:

1.: -a 
2.: sd-a 
3.: sd-g----10-9a 
4.: sda 
5.: s ja 
6.: dd 

Cambia:

safeSequence+delimiter 

con

delimiter+safeSequence 
Cuestiones relacionadas