Java String: Descubre el poder de la inmutabilidad y el rendimiento

Si hay una característica revolucionaria que ha hecho que Java fuera diferente y disruptivo desde el inicio son los Java String con su icónica inmutabilidad desde su diseño y esto no fue ninguna casualidad. Pero hay mucho más de lo que aparenta a simple vista. En este artículo, exploraremos las razones detrás de esta decisión de diseño y las interesantes implicaciones que tiene.

La inmutabilidad como una característica fundamental de Java String

Como dice la documentacion de Java 7: las Strings son constantes y como tal son inmutables, es decir no se pueden modificar; después de que son creados sus valores no pueden ser cambiados.

Pero la cosa no queda allí, debido a que los objetos String son inmutables las ubicaciones de memoria que hacen referencia a la misma cadena pueden ser compartidas en vez de crear nuevas cadenas en memoria logrando con esto un rendimiento mejorado porque seamos sinceros… ¿Qué aplicación de Java no usa algún texto?.

Por si se arrepentían de su decisión los desarrolladores tomaron una medida desde el inicio… el constructor de String, en su versión que recibe un String. Este constructor es una de las mayores fuentes de confusión entre programadores nuevos. A menos que una copia explicita en una nueva dirección de memoria de una cadena de texto sea necesaria, el uso de este constructor es innecesario dado que las Strings son inmutables.

System.out.println("hola" == "hola");
System.out.println("hola" == new String("hola"));
System.out.println("hola".equals("hola"));
System.out.println("hola".equals(new String("hola")));

Java String y el Patrón de Diseño Singleton

Cuando se diseñó le lenguaje se pensó que las cadenas fueran “internas”, es decir que tuvieran instancias únicas compartidas.

Recordemos que el (anti)patrón de diseño Singleton no existía en ese momento, pero los creadores pensaron en una funcionalidad similar mediante el método intern() de String. Este método habla de una “String pool” o un pozo de cadenas (o piscina de cordones si lo traducimos literal), inicialmente vacío, que es en esencia un almacén privado mantenido por la clase String donde se guardan los textos de todas las aplicaciones para la maquina virtual que las ejecute.

representacion astistica de un string pool o piscina de cordones

A diferencia de Singleton puedes tener más de una instancia de String con el mismo contenido si usas el constructor que recibe otro String.

Java String y la ropa interior provocativa

Sí, antes a las cadenas de Java se les llamaba solamente String, pero desde que llegó el lenguaje Basado en Java llamado Groovy llegó con su broma maliciosa de llamar a las cadenas de ese lenguaje como GString. Si eres exclusivamente hispanoparlante tal vez no notes la travesura, pero a alguien en algún momento se le ocurrió hacer un juego de palabras al ponerle la G de Groovy a la palabra String para que sonara como la palabra g-string que significa tanga en inglés gringo para que cada que alguien hablara de cadenas de texto en el lenguaje groovy hablara también de tangas.

Consejos clave para aprovechar al máximo Java String

Esto nos lleva a las siguientes características muy especiales del lenguaje:

  • Reiniciar tu máquina virtual borrará el pool de cadenas, liberando una gran cantidad de memoria.
  • Utilizar las mismas cadenas una y otra vez tendrá un impacto increíble en el desempeño de tu aplicación Java. Aprovecha esta característica para mejorar la eficiencia de tu código.
  • Nunca almacenes contraseñas como cadenas, ya que representan un riesgo de seguridad. En su lugar, utiliza arreglos de caracteres que no se queden en memoria.
  • Evita usar el constructor de String que recibe otra String, a menos que sea absolutamente necesario.
  • Ten en cuenta que a partir de la segunda vez que se usa la misma cadena, se hará referencia al mismo objeto. Esto tiene implicaciones en cuanto al manejo de memoria y el paso por referencia en Java.
  • Usa el operador + con precaución si estas usando una versión de Java menor la 8, ya que en estas versiones crea una nueva cadena. Tras usarlo una sola vez tendrás tres cadenas almacenadas en el pool y ya te imaginaras como acaba eso si tienes tu aplicación corriendo por meses.
  • Evita usar String.format tiene un pésimo desempeño.

Todo acerca del tipo String viene en la especificación del lenguaje en caso de que desees aprender más sobre el tema.

Algunas cosas más avanzadas

¡Pero eso no es todo! Aquí hay algunas ideas más avanzadas sobre Java String que te dejarán impresionado:

  • Las literales de cadenas casi siempre se internan(ver dos puntos después para excepciones a esta regla) al igual que cuando uno le pasa una cadena a String.intern()
  • Las cadenas en el pool de cadenas nunca serán colectadas por el recolector de basura (GC)
  • Si usamos Class.forName para cargar una clase las literales de cadena serán marcadas para recolección cuando la clase sea unloaded.
  • La llamada al constructor de String con una cadena no es una literal de cadena así que esta si será marcada para el GC
  • Si concatenamos en el código se evaluará en tiempo de compilación y la cadena será internada
  • En java 9+, si en tiempo de compilación se usa una cadena concatenada con una variable (no una constante) la cadena tendrá una representación especial
  • Antes de Java7 el String pool estaba ubicado en el PermGen
  • A partir de Java 8 la concatenación usa internamente StringBuilder para evitar crear subcadenas en el String pool y con ello mejorar el rendimiento
  • A partir de Java 9 las cadenas son más ligeras, lo cual te dará mejoras de desempeño solamente con subirle la versión a tu código que tuvieras en Java 8 o inferior

Despedida

Es importante saber estos datos para mejorar como desarrollador Java, a pesar de estar mencionado en la documentación oficial, incluso ChatGPT 3.5 cuando se le enfrenta con un código que presenta problemas debido al pool de cadenas no es capaz de tomarlo en cuenta.


  • Cursos de Código Facilito

    Te comparto aquí mis recomendaciones de cursos de Código Facilito. Codigofacilito.com es una plataforma virtual de cursos en idioma exclusivamente español que inició como un canal de YouTube. Opinión de la plataforma En mi opinión la plataforma aún es incipiente y los cursos necesitan más trabajo, ya que es muy común hallarse con clases de…


  • Cursos de LinkedIn Learning

    Te comparto aquí mis recomendaciones de cursos de Linkedin Learning. LinkedIn Learning es una plataforma virtual de cursos propiedad de Microsoft. Hallarás mucho material en inglés, pues prácticamente todos los cursos vienen con subtítulos en castellano y en la parte técnica son muy buenos debido a la adquisición de Lynda.com. En mi opinión la plataforma…


  • Mockito: Snippets de código

    Estos snippets de código para entrevista acerca de mockito espero te sean de mucha utilidad. Claro que también los puedes usar para tu desarrollo en el día a día. Mock básico Si te llegan a mostrar algo como esto es mejor que sospeches, mockito se usa principalmente para pruebas de integración. Si llegas a ver…


javapro.org