martes, 24 de junio de 2014

Manejo básico de caracteres.


Supongamos que se nos pide realizar un programa que lea una cadena introducida por el teclado del usuario y este muestre:

  • Tamaño de la cadena
  • Cantidad de vocales y consonantes
  • Cantidad de letras en minúsculas y mayúsculas.
  • Mostrar la cadena en Mayúsculas.
  • Mostrar la cadena en Minúsculas.
En este tema se muestra el manejo básico de caracteres en Java.

En la programación hay diversas formas de programar, en este tema se verá de una forma de enseñanza para el lector. 

Se crearan métodos para cada punto que el usuario pide.
En el proceso se mostrará que para la mayoría de los puntos es prácticamente un mismo modelo, pero como objeto de estudio se hará paso por paso y cada punto tendrá su método.



1.- Tamaño de la Cadena.

Java cuenta con la clase String, en la cual contiene diversos métodos que el programador puede hacer uso de ellos. En este caso, se mostrará el método .length();

El método .length() de un objeto String retorna el número de caracteres que contiene.

Creamos un método denominado mostrarTamanio() que reciba una cadena y adentro de el mandamos a imprimir el tamaño de la cadena, haciendo uso del método .length().


    public static void mostrarTamanio(String cadenaLeida) {
        System.out.println("Tamaño de la cadena : " + cadenaLeida.length());
    }

2.- Cantidad de Vocales y Consonantes.

El método que se va a crear cuenta la cantidad de vocales y consonantes, de manera sencilla.
Para esto, se va a ser uso del código ASCII. En el que se muestra que para las letras de la A a la Z en mayúscula su intervalo es de 65 al 90. 

Teniendo en cuenta que:
A = 65
B = 66
C ....
Z = 90

Y lo mismo sucede con las letras en minúsculas, la diferencia es que el intervalo es ahora de 97 al 122, siendo:
a = 97
b = 98
c...
z = 122

Con esto en nuestro favor, se plantea la lógica. Para contar las vocales-consonantes se debe extraer cada letra de la cadena leída por el usuario y comprobar si están en ambos intervalo, si no entra en ninguno significa que no es una letra del abecedario A-Z o a-z.

**Problema : En el código ASCII hace referencia al lenguaje inglés, si el idioma del programador es diferente se deben aplicar los respectivos casos. En este ejemplo se hace uso del lenguaje Español de México. Teniendo los acentos de las palabras en las vocales y la letra Ñ-ñ.

Teniendo en cuenta el problema antes mencionado, Java también cuenta porque esta hecho en inglés, por lo tanto se deben hacer algunas modificaciones a la hora de la lectura de datos por el teclado.

Para esto, al crear la instancia del Objeto Scanner se le agrega la norma ISO-8859-1, dedicada al manejo de caracteres del alfabeto latino.

    
     Scanner s = new Scanner(System.in, "ISO-8859-1");


Haciendo a un lado el problema del alfabeto y de la lectura por teclado, nos disponemos a crear el método cuentaVocales_Consonantes(). El cual recibirá la cadena introducida por el teclado del usuario.

Se crearán 2 contadores inicializados en 0. Uno para contar las vocales y el otro para las consonantes.

Como se menciono antes, se debe extraer cada letra de la cadena leída y comprobar si se encuentra o es igual a los caracteres antes mencionados.

En este ejemplo se hace uso del método de la clase String .charAt(). Al hacer uso de este método nos pide que le enviemos un índice, el cual es el número de la letra que queremos extraer. Al igual que como muchas cosas en la programación, el manejo de caracteres se encuentra indexado en 0 [cero], esto nos quiere decir :

Si queremos extraer la primera letra de Hola sería de esta manera :
      String aux = "Hola"

    char primeraLetra = aux.charAt(0);   // Lo que retornaría la letra H.

*Para extraer la ultima letra se hace uso del método antes visto, .length() que nos da el número de caracteres en la cadena, pero como esta indexado en 0 le restamos -1.

    char primeraLetra = aux.charAt(aux.length()-1);   // Lo que retornaría la letra a.

Teniendo en cuenta esto, se creara un ciclo donde una variable i comenzara en 0 y llegara hasta el tamaño de la cadena -1 , incrementando en cada iteración la i en +1. Nos quedaría una estructura así :

     for (int i = 0 ; i < cadenaLeida.length() ; i++) {
        // lógica del problema....
    }

Teniendo la estructura listas, la cual en todos los métodos se repetirá *[exceptuando en convertitr a mayúsculas-minúsculas], se comienza con la lógica.

Se saca el carácter actual de la cadena, y lo comparo con los intervalos antes mencionados y caracteres especiales.

    char letra = cadenaLeida.charAt(i);

if ((letra >= 65 && letra <= 90) || (letra >= 97 && letra <= 122) || letra == 'ñ' || letra == 'Ñ') {
     // es una letra del abecedario.      
}

Al saber que es una letra del abecedario, se pregunta si es una vocal, tanto en mayúsculas como minúsculas. Y si no son vocales, son consonantes, e incrementan sus respectivos contadores.

    if (letra == 'A' || letra == 'E' || letra == 'I' || letra == 'O' || letra == 'U') {
        contadorVocales++;
    } else if (letra == 'a' || letra == 'e' || letra == 'i' || letra == 'o' || letra == 'u') {
        contadorVocales++;
    } else {
        contadorConsonantes++;
    }

Teniendo este método terminado, el problema es si el usuario ingresa una palabra con acento. El problema se arregla creando otro if preguntando si la letra lleva acento, pero

¿En dónde se colocaría el if ?

El if se coloca al recorrer la palabra letra por letra, cuando se pregunta por los intervalos y los caracteres especiales.

Agregando la linea correspondiente :
            if ((letra >= 65 && letra <= 90) || (letra >= 97 && letra <= 122) || letra == 'ñ' || letra == 'Ñ') {

                if (letra == 'A' || letra == 'E' || letra == 'I' || letra == 'O' || letra == 'U') {
                    contadorVocales++;
                } else if (letra == 'a' || letra == 'e' || letra == 'i' || letra == 'o' || letra == 'u') {
                    contadorVocales++;
                } else {
                    contadorConsonantes++;
                }
            } else if (letra == 'á' || letra == 'é' || letra == 'í' || letra == 'ó' || letra == 'ú') {
                contadorVocales++;
            }

Por último quedaría solo imprimir la respuesta, finalizando el método de esta manera:

    public static void cantidadVocalesConsonantes(String cadenaLeida) {
        int contadorVocales = 0;
        int contadorConsonantes = 0;

        for (int i = 0; i < cadenaLeida.length(); i++) {

            char letra = cadenaLeida.charAt(i);

            if ((letra >= 65 && letra <= 90) || (letra >= 97 && letra <= 122) || letra == 'ñ' || letra == 'Ñ') {

                if (letra == 'A' || letra == 'E' || letra == 'I' || letra == 'O' || letra == 'U') {
                    contadorVocales++;
                } else if (letra == 'a' || letra == 'e' || letra == 'i' || letra == 'o' || letra == 'u') {
                    contadorVocales++;
                } else {
                    contadorConsonantes++;
                }
            } else if (letra == 'á' || letra == 'é' || letra == 'í' || letra == 'ó' || letra == 'ú') {
                contadorVocales++;
            }
        }
        System.out.println("Consonantes : " + contadorConsonantes);
        System.out.println("Vocales : " + contadorVocales);
    }

3.- Cantidad de letras en Mayúsculas y Minúsculas.

Llegamos al método de contar la cantidad de mayúsculas y minúsculas. Re-utilizando el código del punto anterior, se concluye que se debe quitar lineas al código. Las lineas a remover son las preguntas si son vocales o consonantes.

Y ahora el if se modifica, preguntando solamente por los debidos intervalos, de mayúsculas y minúscula y respectivamente pasa lo mismo con los caracteres especiales.

Modificando el nombre de las variables utilizadas anteriormente los contadores se inician desde 0.

        int contadorMayusculas = 0;
        int contadorMinusculas = 0;

Y se recorre la palabra extrayendo las letras e incrementando los contadores en sus respectivos bandos.
Teniendo en cuenta contar los acentos en mayúsculas y minúsculas.
      
    public static void cantidadMayusculas_Minusculas(String cadenaLeida) {

        int contadorMayusculas = 0;
        int contadorMinusculas = 0;

        for (int i = 0; i < cadenaLeida.length(); i++) {
            char letra = cadenaLeida.charAt(i);

            if ((letra >= 65 && letra <= 90) || letra =='Ñ') {
                contadorMayusculas++;
            } else if (letra == 'Á' || letra == 'É' || letra == 'Í' || letra == 'Ó' ||letra == 'Ú' ) {
                contadorMayusculas++;
            } else if ((letra >= 97 && letra <= 122) || letra == 'ñ') {
                contadorMinusculas++;
            } else if (letra == 'á' || letra == 'é' || letra == 'í' || letra == 'ó' ||letra == 'ú' ) {
                contadorMinusculas++;
            }
        }
        System.out.println("Cantidad de Mayúsculas : "+contadorMayusculas);
        System.out.println("Cantidad de Minúsculas : "+contadorMinusculas);
    }

4.- Mostrar la cadena en Mayúsculas

El método para convertir a mayúsculas se encuentra "precargado" en la clase String, llamándose .toUpperCase().

En esta parte creamos un método void que nos imprima en consola la cadena leída por teclado pero en Mayúsculas. Para llamar al método solo se debe agregar al final de la cadena un punto [.]  y el respectivo nombre del método.

Ejemplo:     cadenaLeida.toUpperCase();

    public static void mostrarCadenaEnMayuscula(String cadenaLeida) {
        System.out.println("Cadena en Mayúsculas : " + cadenaLeida.toUpperCase());
    }

5.- Mostrar la cadena en Minúsculas.

Para finalizar, el método para convertir a Minúsculas se llama .toLowerCase().
Se crea un método void que nos imprima en consola la cadena leída por teclado pero en Minúsculas. Para llamar al método solo se debe agregar al final de la cadena un punto [.]  y el respectivo nombre del método.

Ejemplo:
   cadenaLeida.toLowerCase();

    public static void mostrarCadenaEnMinuscula(String cadenaLeida) {
        System.out.println("Cadena en Minúsculas : " + cadenaLeida.toLowerCase());
    }

Para Finalizar :

El código completo:

import java.util.Scanner;

/*
 Supongamos que se nos pide realizar un programa que lea una cadena introducida por el teclado del usuario y este muestre:

 - Tamaño de la cadena leída.
 - Cantidad de vocales y consonantes
 - Cantidad de letras en minúsculas y mayúsculas.
 - Mostrar la cadena en Mayúsculas.
 - Mostrar la cadena en Minúsculas.
 */
public class Main {

    public static void main(String[] args) {
        
        Scanner s = new Scanner(System.in, "ISO-8859-1");

        String cadenaLeida = s.nextLine();

        mostrarTamanio(cadenaLeida);
        cantidadVocalesConsonantes(cadenaLeida);
        cantidadMayusculas_Minusculas(cadenaLeida);
        mostrarCadenaEnMayuscula(cadenaLeida);
        mostrarCadenaEnMinuscula(cadenaLeida);
    }

    public static void mostrarTamanio(String cadenaLeida) {
        System.out.println("Tamaño de la cadena : " + cadenaLeida.length());
    }

    public static void cantidadVocalesConsonantes(String cadenaLeida) {
        int contadorVocales = 0;
        int contadorConsonantes = 0;

        for (int i = 0; i < cadenaLeida.length(); i++) {

            char letra = cadenaLeida.charAt(i);

            if ((letra >= 65 && letra <= 90) || (letra >= 97 && letra <= 122) || letra == 'ñ' || letra == 'Ñ') {

                if (letra == 'A' || letra == 'E' || letra == 'I' || letra == 'O' || letra == 'U') {
                    contadorVocales++;
                } else if (letra == 'a' || letra == 'e' || letra == 'i' || letra == 'o' || letra == 'u') {
                    contadorVocales++;
                } else {
                    contadorConsonantes++;
                }
            } else if (letra == 'á' || letra == 'é' || letra == 'í' || letra == 'ó' || letra == 'ú') {
                contadorVocales++;
            }
        }
        System.out.println("Consonantes : " + contadorConsonantes);
        System.out.println("Vocales : " + contadorVocales);
    }

    public static void cantidadMayusculas_Minusculas(String cadenaLeida) {

        int contadorMayusculas = 0;
        int contadorMinusculas = 0;

        for (int i = 0; i < cadenaLeida.length(); i++) {
            char letra = cadenaLeida.charAt(i);

            if ((letra >= 65 && letra <= 90) || letra =='Ñ') {
                contadorMayusculas++;
            } else if (letra == 'Á' || letra == 'É' || letra == 'Í' || letra == 'Ó' ||letra == 'Ú' ) {
                contadorMayusculas++;
            } else if ((letra >= 97 && letra <= 122) || letra == 'ñ') {
                contadorMinusculas++;
            } else if (letra == 'á' || letra == 'é' || letra == 'í' || letra == 'ó' ||letra == 'ú' ) {
                contadorMinusculas++;
            }
        }
        System.out.println("Cantidad de Mayúsculas : "+contadorMayusculas);
        System.out.println("Cantidad de Minúsculas : "+contadorMinusculas);
    }

    public static void mostrarCadenaEnMayuscula(String cadenaLeida) {
        System.out.println("Cadena en Mayúsculas : " + cadenaLeida.toUpperCase());
    }

    public static void mostrarCadenaEnMinuscula(String cadenaLeida) {
        System.out.println("Cadena en Minúsculas : " + cadenaLeida.toLowerCase());
    }
}


Lo anterior visto, en los que se hace uso de la sentencia if {...} else {...} , también se puede ocupar un switch - case. Ajustándose a lo que el programador sienta mas cómodo.

En otro tema se vera la forma de agrupar todo en solo método. Como se mostró la mayoría de los métodos son repetitivos. 

Lo bueno de la programación es que hay diversas formas de hacer las cosas y uno puede aprender de todo.

Gracias por su atención  :)

2 comentarios: