Está en la página 1de 6

Laboratorio de Programación II.

Grupo C

PRACTICA 4: PUNTEROS(II)

EJERCICIO GUIADOS
Ejercicio 1
En este ejercicio se va a implementar un programa que permite al usuario introducir un
número determinado de palabras y da como resultado la impresión de las palabras por
consola ordenadas de forma descendente. Para ello se va a utilizar la función strcmp(char*,
char*) de la librería estándar del C++ que permite comparar dos cadenas de caracteres.
Dicha función está declarada en el fichero string.h.

Escribir el siguiente código:


#include <iostream.h>
#include <string.h>
void Ordena(char **, int);
void ImprimePalabras(char **, int);
char** ReservayPide(int);
void Libera( char **, int);
void main(void)
{
char **palabras;
int num;
cout << "Numero de palabras:";
cin >> num;
palabras = ReservayPide(num);
cout << "Palabras Introducidas: " << endl;
ImprimePalabras(palabras,num);
Ordena(palabras,num);
cout << "Palabras Ordenadas: " << endl;
ImprimePalabras(palabras,num);
}
char** ReservayPide(int num)
{
char tmp[120];
char **words;
words = new char*[num];
for (int i=0;i<num;i++){
cout << "Introduce la " << i+1 << " palabra:";
cin >> tmp;
words[i] = new char[ strlen(tmp)+1 ];
strcpy( words[i], tmp);
}
return words; //devuelve matriz
}
void Ordena(char **words, int num)
{
for (int i=0;i<num-1;i++){
Laboratorio de Programación II. Grupo A
3
for (int j=i+1;j<num;j++){
if ( strcmp( words[i], words[j]) < 0) {
//al cambiar hay que destruir los vectores
int len1 = strlen(words[i]);
int len2 = strlen(words[j]);
char *tmp1 = new char[len1 +1];
char *tmp2 = new char[len2 +1];
strcpy(tmp1,words[i]); //copiar antes de borrar
strcpy(tmp2,words[j]);
delete [] words[i]; //eliminar vectores
delete [] words[j];

1
Laboratorio de Programación II. Grupo C

words[i] = new char[len2+1]; //nuevos vectores


words[j] = new char[len1+1];
strcpy(words[i],tmp2); //Permutar las cadenas
strcpy(words[j],tmp1);
delete [] tmp1; //eliminar vectores temporales
delete [] tmp2;
}
}
}
}
void ImprimePalabras(char ** words, int Num)
{
for (int i=0;i<Num;i++){
cout << "\t" << words[i] << endl;
}
}
void Libera( char **words, int Num)
{
for (int i=0;i<Num;i++) delete [] words[i];
delete [] words;
}
Como se puede ver en el código del programa , se aprovechan las ventajas de las funciones
para dar mudularidad al ejercicio, con lo cual se logra que la función principal main() tenga
poco código, sólo incluye las llamadas a las funciones. Se han creado 4 funciones:
1. Función char** ReservayPide(int num): Esta función reserva memoria para almacenar
las cadenas y pide al mismo tiempo los datos de cada palabra. Devuelve el vector de
cadenas.
2. Función Ordena(char **, int): Esta función se encarga de ordenar de forma descendente
las palabras que hay en el vector de cadenas. Para ello utiliza la función strcmp(...). Notar
que si hay que cambiar las palabras, se deben copiar las cadenas primero, luego borrar el
espacio que cada cadena ocupa (esto debido a que la longitud de las cadenas pueden ser
diferentes). Finalmente se reserva nuevamente memoria para almacenar las cadenas
cambiadas.
3. Funcion Imprime(char **, int): Se encarga de imprimir a la consola las cadenas que hay
en el vector.
4. Función Libera(char **, int): Su función es liberar la memoria utilizada.

Ejercicio 2
Para reservar memoria dinámica para matrices se siguen los siguientes pasos:
a. Se crea un puntero a punteros del tipo de datos: float **datos;
b. Se reserva memoria para el array de filas: datos = new float*[fil];
c. Se hace un bucle para reservar memoria para col columnas de cada fila:
for (int i=0;i<fil;i++) datos[i] = new float[col];
d. Creada la matriz, se puede trabajar con ella con los índices y los corchetes [].
e. Finalmente, se debe hacer otro bucle para liberar la memoria de cada fila y la asignada al
vector de filas.

En el siguiente ejemplo se ve cómo asignar memoria a una matriz de filxcol:


// fichero matriz.cpp
// crear matrices usando memoria dinamica
#include <iostream.h>
#include <string.h> //para strlen
#include <stdlib.h> //para atoi()
void main(void)

2
Laboratorio de Programación II. Grupo C

{
int fil = 8; //numero de filas
int col = 5; //numero de columnas
float **datos;
datos = new float*[fil]; //vector filas
//reserva memoria para las columnas de cada fila
for (int i=0;i<fil;i++)
datos[i] = new float[col];
//ya puedes usar la matriz
for (int f=0;f<fil;f++)
for (int c=0;c<col;c++) datos[f][c] = (float)rand()/RAND_MAX;
//imprime los valores
for ( f=0;f<fil;f++){
for (int c=0;c<col;c++) {
cout << f << "," << c << ":"<<datos[f][c]<< " ";
}
cout <<endl;
}
//liberar memoria
for (f=0;f<fil;f++) delete datos[f]; //libera filas
delete [] datos; //libera vector
}

Ejercicio 3
En este ejercicio se va a crear un programa capaz de leer desde el teclado un conjunto de frases,
almacenarlas en un "vector de punteros a caracteres". Cada letra (char) es "tratado como si
fuera un número" (una casilla) y por lo tanto almacenar una frase se asemeja a almacenar una
fila de una matriz. Por lo tanto se necesita un doble puntero (char **pfrases) para poder
almacenar un conjunto de frases o palabras. En esta "matriz de letras" el número de columnas
puede variar para cada fila (es strlen(frase)+1). Utilizando una única llamada a la función
strcpy() es posible rellenar una fila completa de dicha matriz de caracteres. Para utilizar dicha
función es necesario incluir el fichero string.h.

// fichero frases.cpp
#include <iostream.h>
#include <string.h>
#include <stdio.h> //para gets()
void main(void)
{
char frase[120];
char** pfrases;
int NumFrases;
cout << "Cuantas frases desea almacenar:";
cin >> NumFrases;
pfrases = new char*[NumFrases]; //Espacio para NumFrases
//pedir datos
for (int i=0;i<NumFrases;i++) {
cout << "Escriba la frase " << i+1 << ":" << flush;
gets(frase);
// +1 porque strlen no guarda para el '\0'
pfrases[i] = new char[strlen(frase)+1];
strcpy(pfrases[i], frase);
}
//sacar datos por consola
for (i=0;i<NumFrases;i++)
cout << "Frase " << i+1 << ":" << pfrases[i] << endl;
//liberar memoria
for (i=0;i<NumFrases;i++) delete pfrases[i];
delete [] pfrases;
}

3
Laboratorio de Programación II. Grupo C

EJERCICIO PROPUESTOS
Ejercicio 1
Se pide crear un programa que haciendo uso de la reserva dinámica de memoria almacene un
número determinado de valores (obtenidos de forma aleatoria, entre 0 y 100) y los ordene de
mayor a menor. El código para obtener los números y para la reserva dinámica de memoria es
dado, y el resto debe ser implementado.
//fichero ordena.cpp
// ordena usando memoria dinamica
#include <iostream.h>
#include <stdlib.h> //para rand()
void main(void)
{
int Num; //Numero de datos
int *datos; //puntero a int
cout << "Cuantos numeros deseas generar:";
cin >> Num;
//asignacion de memoria
datos = new int[Num];
if (datos == NULL) cout << "Error";
//Llenar el vector
for (int i=0;i<Num;i++){
datos[i] = rand() * 100 / RAND_MAX;
}
//ordena los datos -> Hacer aquí el algoritmo
. . .
. . .
//imprime los datos ordenados
for (i=0;i<Num;i++) cout << i << ":" << datos[i] <<endl;
//liberar memoria
delete [] datos;
}

Ejercicio 2
Se pide crear un programa que pida una serie de números al usuario y halle el máximo, el
mínimo y la media aritmética de ellos. Para ello se debe crear una variable puntero tipo
float , pedir al usuario que introduzca el número de datos, y después los datos a calcular.
Recordar que se debe reservar memoria de forma dinámica para almacenar el vector de
dato. La salida del programa debe ser algo así:
Numero de datos: 10
Máximo: 25
Minimo: 4
Media Aritmética: 14.6

Ejercicio 3
Basándose en el ejercicio 2) guiado, se pide realizar un programa que calcule el producto de
dos matrices MatA y MatB con asignación dinámica de memoria. Los pasos a seguir son:
1- Crear dos punteros a punteros.
2- Pedir por teclado las dimensiones de la matriz MatA (filas y columnas).
3- Pedir por teclado sólo las columnas de la matriz MatB, ya que las filas tienen que ser
igual a las columnas de MatA para la multiplicación.
4- Realizar la reserva dinámica de memoria, usando el operador new.
5- Pedir los datos de las dos matrices MatA y MatB.
6- Realizar la multiplicación en dos bucles for anidados.
7- Finalmente se debe sacar por consola las dimensiones de la matriz resultante y los datos
de la matriz resultante.
8- Liberar la memoria asignada, utilizando el operador delete.

4
Laboratorio de Programación II. Grupo C

Ejercicio 4
En este ejercicio se va evaluar un polinomio de cualquier grado:
P(X)=a0+a1x+a2x2+a3x3+…+anxn
Como en un principio no se sabe de qué grado va a ser este polinomio, se debe crear una
variable puntero del tipo double:
double *coeficientes;
A continuación se debe pedir el grado del polinomio y reservar memoria para el array de
coeficientes (utilizando el operador new). Luego, a través de un bucle se empezará a pedir
los coeficientes del polinomio. Finalmente se debe pedir el punto (x) en el que se va a
evaluar el polinomio, cuyo resultado se sacará por la consola. También se debe sacar por la
consola el polinomio que se ha evaluado.

La entrada y salida de datos por la consola podría ser:


>> Introduce el numero de coeficientes: 2
>> Introduce el coeficiente 1: 2.5
>> Introduce el coeficiente 2: 3.5
>> Introduce el valor de x: 2.0
>> El polinomio es: 2.5*X^0 + 3.5*X^1
>> El valor del polinomio en el punto 2.0 es 9.5

Ejercicio 5
Este ejercicio consiste en implementar un algoritmo para el cálculo de la integral definida
de un polinomio entre dos puntos (A y B) dados. El polinomio debe ser de cualquier
grado:
P(X)=a0+a1x+a2x2+a3x3+…+anxn
Los pasos a seguir son:
1. Pedir el grado del polinomio.
2. Crear un array de tipo double para albergar el polinomio (utilizar new).
3. Pedir los coeficientes del polinomio.
4. Pedir los puntos A y B para evaluar la integral (A < B).
5. Pedir el número de subintervalos “n”.
6. Sacar el valor de la integral por consola.
El algoritmo se basa en la división del intervalo (A, B de la figura ) en n subintervalos,
sumando las áreas de éstos. Si los subintervalos son lo suficientemente pequeños el área de
cada subintervalo se puede aproximar al área de un trapecio. En definitiva, la integral se
puede aproximar como:

∫ f ( x) ≈ ∑
b
((f(xi)+f(xi+1)/2)*(xi+1-xi))

5
Laboratorio de Programación II. Grupo C

Ejercicio 6
Este ejercicio consiste en hacer un programa que cuente cuantas veces se repiten las vocales
(se deben contar las mayúsculas y las minúsculas)en un texto dado por el usuario. La
estructura del programa debe ser la siguiente:
#include <iostream.h>
#include <string.h>
char *PideTexto();
void ContarVocales(char *, int []);
void Imprime(int []);
void main()
{
char *texto;
int Num[5];
texto = PideTexto();
ContarVocales(texto,Num);
Imprime(Num);
delete [] texto; //libera memoria
}

A continuación se explican cada una de las funciones llamadas desde main:


1.La función PideTexto devuelve un puntero a la cadena que el usuario ha escrito.
2.La función ContarVocales recibe el array que contiene el texto y otro array de enteros,
en el cual va a devolver cuantas veces se repite cada una de las vocales, es decir, en
Num[0] vendrán las veces que se repite la vocal a , en Num[1] la vocal e y así
sucesivamente.
3.La función Imprime recibe el array de enteros e imprime en la consola lo que ha
encontrado.

ENTREGA DE LOS EJERCICIOS


La forma de entregar la práctica será a través de la asignatura virtualizada en el campus virtual. En la
asignatura virtualizada verás una serie de enlaces, entre ellos, hay uno titulado como prácticas. Navega sobre
dicho enlace, y verás que hay un grupo con los apellidos de los integrantes de los grupos. Dicho grupo de
trabajo tiene asociado una carpeta sobre la que puedes subir , eliminar o editar archivos(Accedes usando
Editar Archivos). Zippea el trabajo correspondiente, y dentro del zip incluye un archivo de texto en que
aparezcan los nombres de los que formáis el grupo. Etiqueta el archivo zip con el nombre
LabnApellidoApellido.zip. Por ejemplo si Juan Martínez Martin y Silvia Pérez García están en el laboratorio
1, y forman un grupo etiquetan su zip como Lab1MartinezPerez.zip. A continuación usa la opción cargar
que hay en la parte derecha del área donde te encuentras, y te permitirá subir archivos desde tu disco duro.
Almacénalo en la carpeta correspondiente al grupo al que perteneces.

Tenéis de plazo para subir la correspondiente práctica 4 hasta este viernes día 3 de Noviembre. Acabado el
plazo no se podrán subir las prácticas, y se considerará como práctica no entregada. Si tienes alguna duda o
problema sobre el procedimiento de entrega no dudes en preguntar.