Calcular longitud de cadena C++ (punteros)

Iniciado por Bob1098, 15 Septiembre 2014, 16:51 PM

0 Miembros y 2 Visitantes están viendo este tema.

Bob1098

Hola a todos, estoy intentando resolver un ejercicio de c++ que dice lo siguiente:

"Escribir un programa con una función que calcule la longitud de una cadena de caracteres. El nombre de la función será LongitudCadena, debe devolver un int, y como parámetro de entrada debe tener un puntero a char.
En esta función no se pueden usar enteros para recorrer el array, usar sólo punteros y aplicar aritmética de punteros.
En main probar con distintos tipos de cadenas: arrays y punteros."

Supongo que no vale esto de recorrer el array con un entero y luego devolver dicho entero, por tanto he probado con esto:

Código (cpp) [Seleccionar]
#include <iostream>

using namespace std;

int LongitudCadena(char*);

int main() {
char cadena[10];
char *pCadena = 0;

cout << "Introduce una cadena como array: ";
cin >> cadena;
cout << "Su tamano es: " << LongitudCadena(cadena) << ". " << endl;
cout << "\nIntroduce una cadena como puntero: ";
cin >> *pCadena;
cout << "Su tamano es: " << LongitudCadena(pCadena) << ". " << endl;

cin.sync();
cin.get();
return 0;
}

int LongitudCadena(char *a) {
char *p, *q;
p = a;
q = a;
while (*a) q++;
return q-p;
}


Seguro que hay una forma mucho mas simple, pero aun soy nuevo con esto de los punteros y no los comprendo muy bien. Espero que se pueda encontrar el fallo.

Un saludo.

ivancea96

Dado que la 'a' no cambia, "while(*a)" dará bucle infinito.

Puedes poner, en su lugar: "while(*q) ++q;".

Además, si quieres usarlo para otros tipos, deberías poner: "return (q-p)/sizeof(char);". Claro que en este caso, al ser char, no tiene mucho sentido jaja

En todo caso yo quitaría la variable 'p', que sobra. En vez de "return q-p;", poner "return q-a;".

Danyfirex

Podría ser algo así.


Código (cpp) [Seleccionar]
unsigned int Largo(char * ptr){
unsigned int len=0;

while (*ptr++)len++;
return len;
}


Saludos

eferion

Cita de: Danyfirex en 15 Septiembre 2014, 18:51 PM
Podría ser algo así.


Código (cpp) [Seleccionar]
unsigned int Largo(char * ptr){
unsigned int len=0;

while (*ptr++)len++;
return len;
}


Saludos

¿Y la aritmética de punteros donde queda?

Tratando el tema dejado por ivancea96, tal y como está planteado el enunciado no tiene ningún sentido hacer un código más genérico por varias razones:

* Únicamente las cadenas de caracteres tienen la obligación de terminar con caracter nulo.
* La función no admite un segundo parámetro que permita identificar el final de la cadena.

Si se dispusiese de información adicional y de algo más de flexibilidad sería fácil hacer una función genérica que calculase el tamaño de un array cualquiera.


ivancea96

Hablaba para poder portarlo a widechar, por ejemplo. Pero era una mera curiosidad, no digoque sea necesario xD

Blaster

Cita de: Bob1098 en 15 Septiembre 2014, 16:51 PM
Seguro que hay una forma mucho mas simple, pero aun soy nuevo con esto de los punteros y no los comprendo muy bien.

Quedaría mas o menos así :

Código (cpp) [Seleccionar]
size_t LongitudCadena(const char *str)
{
    const char *s;
    for (s = str; *s; ++s);
    return(s - str);
}


No hay necesidad de usar un segundo puntero

Un Saludo


Bob1098

Vale, muchas gracias a todos por las respuestas. Aunque estoy sea una cosa muy simple me sirve para intentar comprender el funcionamiento de los punteros, ya que según he leído por ahí los punteros usados correctamente son una herramienta muy poderosa.

Un saludo y gracias.

rir3760

Otra parte que se debe corregir para que el programa funcione correctamente es:
Código (cpp) [Seleccionar]
int main()
{
   char cadena[10];
   char *pCadena = 0;
   
   cout << "Introduce una cadena como array: ";
   cin >> cadena;
   cout << "Su tamano es: " << LongitudCadena(cadena) << ". " << endl;
   cout << "\nIntroduce una cadena como puntero: ";
   cin >> *pCadena;
   cout << "Su tamano es: " << LongitudCadena(pCadena) << ". " << endl;


Ahí el valor inicial de "pCadena" no es valido, hay que cambiarlo a:
Código (cpp) [Seleccionar]
int main()
{
   char cadena[10];
   char *pCadena = cadena;
   
   cout << "Introduce una cadena como array: ";
   cin >> cadena;
   cout << "Su tamano es: " << LongitudCadena(cadena) << ". " << endl;
   cout << "\nIntroduce una cadena como puntero: ";
   cin >> pCadena;
   cout << "Su tamano es: " << LongitudCadena(pCadena) << ". " << endl;


Sin embargo no es un buen ejercicio para la practica de punteros por lo siguiente:
1) Cuando se utiliza el operador ">>" con el objeto "cin" (como en tu ejemplo) se lee una palabra y se debe indicar mediante un puntero donde debe almacenarse.
2) Ese puntero se genera de forma automática al utilizar el identificador del array (este es "cadena").

En pocas palabras no hay tal diferencia entre array y puntero en este caso, supongo lo que quiere enseñar el profesor es el uso de los operadores "[]" y "*".

Un saludo
C retains the basic philosophy that programmers know what they are doing; it only requires that they state their intentions explicitly.
--
Kernighan & Ritchie, The C programming language

Bob1098

Cita de: rir3760 en 16 Septiembre 2014, 17:15 PM
Otra parte que se debe corregir para que el programa funcione correctamente es:
Código (cpp) [Seleccionar]
int main()
{
   char cadena[10];
   char *pCadena = 0;
   
   cout << "Introduce una cadena como array: ";
   cin >> cadena;
   cout << "Su tamano es: " << LongitudCadena(cadena) << ". " << endl;
   cout << "\nIntroduce una cadena como puntero: ";
   cin >> *pCadena;
   cout << "Su tamano es: " << LongitudCadena(pCadena) << ". " << endl;


Ahí el valor inicial de "pCadena" no es valido, hay que cambiarlo a:
Código (cpp) [Seleccionar]
int main()
{
   char cadena[10];
   char *pCadena = cadena;
   
   cout << "Introduce una cadena como array: ";
   cin >> cadena;
   cout << "Su tamano es: " << LongitudCadena(cadena) << ". " << endl;
   cout << "\nIntroduce una cadena como puntero: ";
   cin >> pCadena;
   cout << "Su tamano es: " << LongitudCadena(pCadena) << ". " << endl;


Sin embargo no es un buen ejercicio para la practica de punteros por lo siguiente:
1) Cuando se utiliza el operador ">>" con el objeto "cin" (como en tu ejemplo) se lee una palabra y se debe indicar mediante un puntero donde debe almacenarse.
2) Ese puntero se genera de forma automática al utilizar el identificador del array (este es "cadena").

En pocas palabras no hay tal diferencia entre array y puntero en este caso, supongo lo que quiere enseñar el profesor es el uso de los operadores "[]" y "*".

Un saludo

Vale, ya lo voy pillando. Gracias por la respuesta.

Un saludo

do-while

#9
¡Buenas!

Esta función es muy sencilla también:

int longitud(char *s)
{
    if(!(*s))
        return 0;

    return 1 + longitud(s + 1);
}


¡Saludos!

PD: o con un cuerpo de una sola línea: XD

int longitud(char *s)
{
    return (*s) ? 1 + longitud(s + 1) : 0;
}
- Doctor, confundo los números y los colores.
- Vaya marrón.
- ¿Marrón? ¡Por el culo te la hinco!