[ Foro de C ]

Agenda

04-Jan-2010 02:12
emuletas yp
7 Respuestas

Hola otra vez. He llegado al manejo de ficheros. Mis problemas son los siguientes. He comenzado a crear el programa, el código fuente está incompleto, pero es compilable.

PROBLEMA-1: No sé que poner en fopen(nombre, "aquí") para que si el archivo no existe, que lo cree, pero que si existe, que no lo sobrescriba.

PROBLEMA-2: AL ejecutar el programa, este es el resultado (todavía está desordenado XD):

cesar@cesar-laptop:~$ ./agenda
AGENDA TELEFÓNICA
----------MENÚ----------###Introduce el número de la opción###
1.Añadir un dato
2.Visualizar nombres de la agenda
3.Mostrar datos de una persona
4.Salir1
Introduce los datos de la nueva persona
Introduce el nombre de la persona
Segmentation fault
cesar@cesar-laptop:~$

PROBLEMA-3: Al cerrar el programa, volver a abrilo, añadir un nuevo dato, en el for empezará desde 0 y me substituirá los datos que ya tengo, como puedo evitar eso?

Código fuente aquí:

#include <stdio.h>

main()

{



FILE* fichero;

char nombre="agenda.dat";

fichero=fopen(nombre,"r+t");

struct {

char nombre[80], direccion[80], email[80];
int movil;
short dia, mes, anyo;

}persona[100];

menu:

printf("AGENDA TELEFÓNICA\n----------MENÚ----------");
printf("###Introduce el número de la opción###\n");
printf("1.Añadir un dato\n");
printf("2.Visualizar nombres de la agenda\n");
printf("3.Mostrar datos de una persona\n");
printf("4.Salir");


int getmenu, i;
char sn;
scanf("%d", &getmenu);
switch(getmenu)

{
case 1:

for (i=0; i<=100; i++){
printf("Introduce los datos de la nueva persona\n");
printf("Introduce el nombre de la persona\n");
fscanf(fichero, "%s", &persona[i].nombre);
printf("Introduce la dirección de la persona\n");
fscanf(fichero, "%s", &persona[i].direccion);
printf("Introduce el email de la persona\n");
fscanf(fichero, "%s", &persona[i].email);
printf("Introduce el teléfono móvil de la persona\n");
printf("Introduce la fecha de nacimiento (d/m/a)");
fscanf(fichero, "%hd/%hd/%hd", &persona[i].dia, &persona[i].mes, &persona[i].anyo);

printf("¿Quieres volver a introducir otra persona en la agenda?\n (s/n)");
gets(sn);
if (sn=="s") continue;
if (sn=="n"){

goto menu;
fscanf(fichero, i, &i); /* CON ESTE PASO, LO QUE INTENTO ES
QUE SE GUARDE EN EL ARCHIVO AGENDA.DAT
POR QUÉ VALOR PARA i IBA CONTANDO EL FOR ANTES DE
    SALIR DEL PROGRAMA, PARA INTENTAR SOLUCIONAR EL PROBLEMA 3.
SEGURAMENTE ESTO TIENE OTRA SOLUCIÓN MÁS FÁCIL. ESPERO QUE ME PODAIS AYUDAR*/
   }
   
       }

}

}

Por supuesto, si podeis simplificar mi codigo fuente y/o corregirlo, hacedlo XD y decidmelo porfavor.


Un saludo!


04-Jan-2010 11:46
mario moreno

Hola, no he podido estudiar todos tus problemas, pero en cuanto al primero te recomendaría que leyeses la pag. 93 del pdf, el punto 6.6.

Desde mi opinión te daré un consejo, intenta por ti mismo averiguar dónde pueden estar los errores, busca en google, fijate en post anteriores que algunos ya han tratado esos temas. Es la única forma de avanzar. Es mejor llegar a la solución por ti mismo a que te la den hecha.

El segundo problema creo que tiene que ver con el uso de "fscanf".

;). Suerte.


05-Jan-2010 10:09
emuletas yp

No entiendo qué estoy haciendo mal, ya lo he dicho, llevo bastante tiempo dándole vueltas a ese rollo.


06-Jan-2010 15:25
Nacho Cabanes (+32)

Tienes varios fallos. Por ejemplo:

--------------------
fichero=fopen(nombre,"r+t");
--------------------

En general, el modo de apertura "r+t" no será útil, porque en un fichero de texto no tiene sentido abrir para escribir en una posición intermedia: o lo abres para leer (modo "rt"), o lo creas (modo "wt") o añades al final (modo "at").


--------------------
printf("1.Añadir un dato\n");
...
case 1:
for (i=0; i<=100; i++){
printf("Introduce los datos de la nueva persona\n");
...
--------------------

Si quieres añadir un dato, no tiene sentido usar un "for", que es una estructura repetitiva. Además, tu "for" va desde 0 hasta 100, mientras que tu "array" tiene 100 datos, no 101 (y, por tanto, va de 0 a 99).

--------------------
printf("Introduce el nombre de la persona\n");
fscanf(fichero, "%s", &persona[i].nombre);
--------------------

Si esperas que el usuario teclee algo, tendrás que leer con "scanf" o con "gets", no con "fscanf", que sirve para leer de fichero.

--------------------
if (sn=="s") continue;
--------------------

Lo razonable es no usar un "for" si no quieres pedir nada más que un dato. Si aun así, decides usar un "for" con la intención de interrumpirlo, ten presente que la orden que interrumpe un bucle no es "continue" sino "break".

Además, y lo que es más grave: el valor de una cadena de texto NUNCA se puede comprobar con ==, se debe hacer siempre con "strcmp".


--------------------
fscanf(fichero, i, &i); /* CON ESTE PASO, LO QUE INTENTO ES
QUE SE GUARDE EN EL ARCHIVO AGENDA.DAT
POR QUÉ VALOR PARA i IBA CONTANDO EL FOR ANTES DE
--------------------

La orden para escribir es "fwrite" o "fprintf", pero nunca "fscanf", que es una orden de lectura. Hay varias formas de saber cuantas fichas llevas:

a) Lees mientras que haya datos, de forma que aumentas el contador con cada dato que lees.

b) Ya que tienes un array de 100, guardas todo el array, sin preocuparte de cuántos de esos datos no están usados realmente, y cuando lees compruebas cuantos están vacíos (aunque esto tiene una complicación adicional, en la que no voy a entrar ahora).

c) Antes de todos los datos (o después de todos ellos) guardas el contador de datos usados.


--------------------

Como conclusión:

- Tienes errores razonables para alguien que está aprendiendo a manejar ficheros, como lo de usar "r+" en vez de "a".

- Pero también tienes varios errores que muestran que todavía no dominas los temas anteriores (como leer en vez de escribir, desbordar la capacidad de un array, el uso incorrecto de continue, analizar cadenas usando "==", mezclar scanf con gets, etc).

Por eso, yo te recomendaría que no tuvieras prisas y miraras todos los ejercicios de repaso anteriores. He añadido bastantes nuevos, que te ayudarán a asentar los conocimientos. Algunos de ellos están resueltos. Todavía no está lista la nueva versión del PDF, pero los puedes ir consultando en la web. Los tienes en:

http://www.nachocabanes.com/c/curso/c_soluciones.php


08-Jan-2010 14:26
emuletas yp

c) Antes de todos los datos (o después de todos ellos) guardas el contador de datos usados.

Una pregunta. Se puede guarda una variable en un fichero?

Algo como fprintf(fichero, "%s", i=9); ??

Eso es lo único que no acabo de entender. Por lo demás, el resto de errores los he localizado l poco de preguntar, sobre todo el de

if(nombre==i) printf ("%d", 1); por ejemplo, sí es un fallo muy gordo.

Tambien lo de fscanf, porque yo pensaba que era para leer los datos del teclado y guardarlos en un fichero, pero en realidad creo que debería hacer esto:

printf("Introduce un dato\n");

scanf("%s", &frase);

fprintf(fichero, "%s\n", frase);

O algo así creo.

Gracias por vuestra ayuda. SI puedes responderme mi primera pregunta, puedo hacer la agenda.

Aquí tengo otra:

si hago esto:

#include <stdio.h>

main()

{

prinf("------------------\n");

char nombre="C:\WINDOWS\kernel32.dll"
FILE* fichero;

fichero: fopen(nombre, "wt");

fputs("--------\n", fichero);

fclose(fichero);

}

Esto sería un "virus"? Osea, esto sobrescribiría kernel32.dll for un archivo de texto con el contenido ----------?

O no? En caso de que no, porque? Porque he escrito mal el código o por que lo proteje el sistema?

Esto solo sirve de ejemplo!


08-Jan-2010 21:10
emuletas yp

Me h equivocado: fichero=fopen etcetcetc


12-Jan-2010 01:08
Nacho Cabanes (+32)

Sí se puede guardar una variable en un fichero, bien sea en un fichero de texto (usando "fprintf", pero con un "%d" si es un dato numérico), o en un fichero binario (usando "fwrite").

Y sobre si ese programa sería un virus... no, no lo es. Sería un programa nocivo, que podría corromper el sistema (al menos en las primeras versiones de Windows, o en cualquier otro sistema operativo igual de poco seguro). Pero para que sea un virus, no basta con que sea nocivo, también tiene que ser capaz de "propagarse" de un ordenador a otro.


12-Jan-2010 14:44
emuletas yp

Sí se puede guardar una variable en un fichero, bien sea en un fichero de texto (usando "fprintf", pero con un "%d" si es un dato numérico), o en un fichero binario (usando "fwrite").

Aún no he llegado a los binarios, con caaalma :D

"Pero para que sea un virus, no basta con que sea nocivo, también tiene que ser capaz de "propagarse" de un ordenador a otro". :O

Eso no es un gusano más que un virus? Me refiero a si es malware. Es más, eso sería detectado por un antivirus?
Como un antivirus detecta si un programa es malicioso sin el código fuente presente?

Gracias por la ayuda

Emuletas






(No se puede continuar esta discusión porque tiene más de dos meses de antigüedad. Si tienes dudas parecidas, abre un nuevo hilo.)