Dada una cadena que no es demasiado larga, ¿cuál es la mejor manera de leerla línea por línea?
Sé que puedes hacer:
BufferedReader reader = new BufferedReader(new StringReader(<string>));
reader.readLine();
Otra forma sería tomar la subcadena en el eol:
final String eol = System.getProperty("line.separator");
output = output.substring(output.indexOf(eol + 1));
¿Alguna otra forma quizás más simple de hacerlo? No tengo problemas con los enfoques anteriores, solo estoy interesado en saber si alguno de ustedes sabe algo que pueda parecer más simple y más eficiente.
Respuestas:
También puedes usar el
split
método de String:Esto le da todas las líneas en una práctica matriz.
No sé sobre el rendimiento de la división. Utiliza expresiones regulares.
fuente
line.separator
y alguien más la lee en Windows usandoline.separator
, todavía está jorobada. Eso no significa que los codificadores incompetentes hagan cosas estúpidas, es solo cómo funcionan las cosas (no siempre).También existe
Scanner
. Puedes usarlo comoBufferedReader
:Creo que este es un enfoque un poco más limpio que los dos sugeridos.
fuente
Como estaba especialmente interesado en el ángulo de eficiencia, creé una pequeña clase de prueba (a continuación). Resultado para 5,000,000 líneas:
Como de costumbre, los tiempos exactos pueden variar, pero la relación es cierta, sin embargo, a menudo lo he ejecutado.
Conclusión: los requisitos "más simples" y "más eficientes" del OP no pueden satisfacerse simultáneamente, la
split
solución (en cualquier encarnación) es más simple, pero laReader
implementación supera a las demás.fuente
lines()
función que devuelve unaStream<String>
de las líneas, que puede recopilar en una lista si lo desea, o procesar la secuencia.Usando Apache Commons IOUtils puede hacerlo bien a través de
No está haciendo nada inteligente, pero es agradable y compacto. También manejará transmisiones, y puede obtener una
LineIterator
también si lo prefiere.fuente
IOUtils.readlines(Reader)
arroja unIOException
. Aunque esto probablemente nunca sucederá con un StringReader, tendrás que atraparlo o declararlo.Solución utilizando
Java 8
características comoStream API
yMethod references
o
fuente
Desde Java 11, hay un nuevo método
String.lines
:Uso:
fuente
Puede usar la API de transmisión y un StringReader envuelto en un BufferedReader que obtuvo una salida de transmisión de líneas () en Java 8:
Da
Al igual que en la línea de lectura de BufferedReader, los caracteres de nueva línea no están incluidos. Se admiten todo tipo de separadores de nueva línea (incluso en la misma cadena).
fuente
También puedes usar:
Si eso no funciona, intente reemplazar
\n
con\r\n
.fuente
O utilice la nueva cláusula try with resources combinada con Scanner:
fuente
Puede probar la siguiente expresión regular:
Código:
Salida:
fuente
El enfoque más fácil y más universal sería usar la expresión regular
Linebreak matcher
\R
que coincida conAny Unicode linebreak sequence
:@ver https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/regex/Pattern.html
fuente