Skocz do zawartości

Zarchiwizowany

Ten temat jest archiwizowany i nie można dodawać nowych odpowiedzi.

zizou666

C i baza danych:

Polecane posty

Krotko i do rzeczy. Mam za zadanie zrobic baze danych. Mam to zrobic na strukturach. Jako, ze ucze sie dopiero C takze mam pewnien problem. W ponizszym programie przy kompilacji (dokladnie przy deklarowaniu zmiennej typu baza) wyskakuje mi blad, konkretnie " "friend" can only be specified inside a class". Program robie w oparciu o pewna ksiazke i jest tam dosc podobny przyklad. Wszystko wydaje mi sie takie same. Moze to przez Deva, bo w nim programuje. Dzieki wszystkim za pomoc z gory. A oto kod (za wszelkie lamerskie pomylki przepraszam najmocniej, alem poczatkujacy, aha i program niedokonczony bo przetestowalem wczesniej i blad wywalilo juz wtedy ;)):

/*baza na strukturach*/

#include<stdio.h>

#define MAXIMIE 15

#define MAXNAZW 15

#define MAXUL 15

#define MAXMIEJSC 15

#define MAXMAIL 20

#define MAXPLEC 2

struct baza

{

char imie[MAXIMIE];

char nazwisko[MAXNAZW];

char ulica [MAXUL];

char miejsowosc [MAXMIEJSC];

char email [MAXMAIL];

char plec [MAXPLEC];

int dzien, miesiac, rok, nrdom, kodp1, kodp2, telefon, pesel;

};

int main (void)

{

struct baza friend;

printf("Podaj prosze imie osoby\n");

gets(friend.imie);

printf("Podaj prosze nazwisko\n");

gets(friend.nazwisko);

printf("Podaj ulice\n");

gets(friend.ulica);

printf("Podaj nr domu\n");

scanf("%2d", &friend.nrdom);

printf("Podaj kod pocztowy (rozgranicz spacja)\n");

scanf("%2d" "3d", &friend.kodp1, &friend.kodp2);

printf("Podaj miejsowosc\n");

gets(friend.miejscowosc);

printf("Podaj nr telefonu\n");

scanf("%9d", &friend.telefon);

printf("Podaj email\n");

gets(friend.email);

printf("Podaj plec\n");

gets(friend.plec);

printf("Podaj nr pesel\n");

scanf("%11d", &friend.pesel);

printf("Informacje o osobie:\n");

printf("%s %s\n", friend.imie, friend.nazwisko);

printf("Adres zamieszkania: %s %2d %2d-%3d %s\n", friend.ulica, friend.nrdom, friend.kodp1, friend.kodp2, friend.miejsowosc);

return 0;

}

EDIT: Problem czesciowo rozwiazany. Dokladniej rzecz biorac z" friendem" nie mam juz problemu ;) Mam go natomiast z inna sprawa. Podczas wyswietlania informacji o uzytkowniku dane znakowe pokazuja sie bez zarzutu. Natomiast liczby calkowite pokazuja sie albo z przypadku, albo wogole sie nie pokazuja. Nie wiem czy jest to jakis rodzaj przepelnienia? Chyba nie, skoro nawet dwucyfrowy numer domu jest blednie wyswietlany.

Link do komentarza
Udostępnij na innych stronach

Tak, to faktycznie przeoczylem, ale nie chodzilo mi o to. Problem polega na pozniejszym wyswietleniu informacji o uzytkowniku. Wprowadzam dane i przy wyswietleniu znaki wyswietlaja sie wporzadku natomiast cyfry to np. 229352 zamiast peselu itp. I wlasnie mysle, ze to nie przez zbyt dluga liczbe, bo przy malych wartosciach dzieje sie to samo. Przy dokonczonym programie jest tak samo.

Link do komentarza
Udostępnij na innych stronach

Odswiezam ten stary temat, gdyz wracam po pewnej przerwie do mojej bazy. Program wyglada troche lepiej, jednak mam pytanie. Mianowicie nie mam pojecia jak uczynic go idiotoodpornym, czyli po prostu sprawic, aby np przy pobieraniu nazwiska podczas wpisania cyfr wyswetlil blad i powrocil do momentu wpisywania. Wszystkie zmienne (np imie, nazwisko, telefon itp.) sa zadeklarowane za pomoca funkcji char (gdyz przy int w zmiennych typu tel, nr domu, nie wyswietlalo mi cyfr tylko jakies wartosci z kosmosu). Nie wiem jak zrobic warunek, zeby podczas wpisywania np imienia wyswietlilo blad jesli dam np "1" i enter, to samo w druga strone. Mam nadzieje, ze mozna zrozumiec to co napisalem. Z gory dzieki za pomoc.

Link do komentarza
Udostępnij na innych stronach

Twój problem z wypisywaniem wziął się właśnie z błędnego wczytywania. Bezsensu jest wczytywać dane jako char[] kiedy wiadomo, że potrzebujesz liczb.

Do idioto odporności polecam pętle while

char name[64];
name[0] = 0;
bool done = false;
while (false == done)
{
  scanf(..., name);
  unsigned int length = strlen(name);
  bool isDone = true;
  for (unsigned int i = 0; i < length; i++)
  {
    if (false == isalpha(name[i])
    {
      isDone = false;
      break;
    }
  }
  done = isDone;
}

Można to ładniej zapisać ;)

W przypadku liczb

while (1 == scanf(..., &liczba1))

while (2 == scanf(..., &liczba1, &liczba2))

itd.

Link do komentarza
Udostępnij na innych stronach

Dobra, problem glupotoodpornosci rozwiazany, ale zawilosci ciag dalszy :D Tym razem wyloze juz wszystkie problemy jakie mi pozostaly na lawe.

Otoz po pierwsze: z numeru pesel trzeba wyciagnac plec. Odpowiada za nia 9 cyfra bodajze. Jesli jest parzysta to osoba jest kobieta, jesli nie, jest facetem. Z peselu trzeba tez wyciagnac date urodzenia (i to chyba jest trudniejsze niz plec, gdyz 2 cyfry trzeba przypisac jakos po kolei do jednej zmiennej i tak dla roku, miesiaca i dnia). Nastepna sprawa to edycja danych. Tutaj kombinowalem dlugo i mozolnie, ale specjalnie do niczego nie doszedlem. Wreszcie ostatnim problemem jest zapisywanie i wczytywanie do pliku. Jak by jakas dobra dusza nakierowala mnie chociarz troche to bede wdzieczny ;)

Link do komentarza
Udostępnij na innych stronach

Skoro chcesz analizować PESEL jako zbór cyfr, to może wczytaj go sobie jako tablicę char.

Parzystość sprawdza się tak:

if (0 == x % 2)
{
  //parzysta
}
else
{
  //nie parzysta
}

PESEL: RRMMDDXXXXX

char rokStr[3];
rokStr[0] = PESEL[0];
rokStr[1] = PESEL[1];
rokStr[2] = 0;
unsigned int rok = atoi(rokStr);

I tak samo dla miesiąca i dnia.

Link do komentarza
Udostępnij na innych stronach

unsigned int rok = atoi(rokStr);

Nie do konca rozumiem ten fragment. Moglbys jakos wyjasnic, o co tutaj biega? :D

EDIT. Juz sprawdzilem czym jest "atoi" wiec problem nieaktualny. Znaczy sie pozostale fragmenty programu pozostaja dalej kwestia otwarta, ktorej jeszcze nie zrobilem, wiec za pomoc odnosnie ich rowniez bede wdzieczny :D

Link do komentarza
Udostępnij na innych stronach

Zapis do pliku ? No to zależy jak ten plik ma wyglądać. Jeżeli to ma być baza danych tylko dla programu to najprościej utworzyć sobie strukturę:

struct Osoba
{
  unsigned int Rok;
  unsigned int Miesiac;
  unsigned int Dzien;
  bool Mezczyzna;
  char Imie[32];
  char Nazwisko[64];
  ...
};

W pliku na początku umieścić liczbę rekordów, a potem wszystkie dane.

Taką strukturę zapisuje się do pliku funkcją fwrite. Jest to zapis binarny, tak samo można zapisać liczbę rekordów.

Odczyt odbywa się analogicznie funkcją fread.

Edycja ?

Ja zrobiłem to tak, że pod klawiszami funkcyjnymi były polecenia, różne w zależności od stanu programu. Na dole był pasek statusu, na górze podpowiedzi, który klawisz co aktualnie robi.

Był tryb przeglądania rekordów. Był tryb dodawania rekordów. Był tryb edycji istniejących.

Link do komentarza
Udostępnij na innych stronach

No dobra, edycja zrobiona, pozostalo mi tylko to zapisywanie do pliku. Teoretycznie wydaje sie to bardzo prosta sprawa, ale mam jednak z tym problem. Otoz mam cos takiego:

  
  zapis:
           int s; //deklaracja zmiennej odpowiedzialnej za numer zapisywanej osoby    
           s=0;
           if (s<=licznik) //licznik odpowiada za lczbe osob w bazie
           {          
           FILE *fp;
           if ((fp=fopen("baza.txt", "w"))==NULL) {
           printf ("Nie mogę otworzyć pliku baza.txt do zapisu!\n");
           exit(1);
           }
           fprintf (fp, "%s\n",bibl[s].imie ); /* zapisz nasz łańcuch w pliku */
           fprintf (fp, "%s\n",bibl[s].nazwisko );
           s++;     }
           fclose (fp);

Problem polega na tym, ze jesli dam zamykanie pliku poza petla "if", to kompilator traktuje "fp" jako jakas nowa zmienna i wywala blad. A jesli dam go w petli, to i tak nie bedzie mi dopisywal kolejnych osob, zrobi to tylko dla pierwszej. Udalo mi sie zrobic zapisywanie dla konkretnej osoby, ale chce, aby byly zapisywane wszystkie, ktore sa w bazie. Dzieki z gory za pomoc.

Link do komentarza
Udostępnij na innych stronach

Zrob zwykla petle for i otwieranie i zamykanie pliku daj poza petla i bedzie dzialac ;-)

FILE *fp;
if ((fp=fopen("baza.txt", "w"))==NULL) {
           printf ("Nie mogę otworzyć pliku baza.txt do zapisu!\n");
           exit(1);
for(){}
fclose(fp);

Link do komentarza
Udostępnij na innych stronach

Alez to bylo proste :D Dzieki wielkie za pomoc.

Kurcze i znowu mam problem, tym razem z wczytywaniem danych ;)

     odczyt:
           {
           printf("Podaj nazwe pliku do odczytu:\n");
           scanf("%s", &nazwa);                  
           FILE *fp;
           if ((fp=fopen(nazwa, "r"))==NULL) {
           printf ("Nie moge otworzyc pliku %s do odczytu!\n", nazwa);
           goto odczyt;
           }
           fscanf (fp, "%s\n", &bibl[licznik].imie );
           fscanf (fp, "%s\n",&bibl[licznik].nazwisko );
           fscanf (fp, "%s ",&bibl[licznik].ulica );
           fscanf (fp, "%s\n",&bibl[licznik].nrdom );
           fscanf (fp, "%s\n",&bibl[licznik].kodp );
           fscanf (fp, "%s\n",&bibl[licznik].miejscowosc );
           fscanf (fp, "%s\n",&bibl[licznik].telefon );
           fscanf (fp, "%s\n",&bibl[licznik].email );
           fscanf (fp, "%s\n",&bibl[licznik].pesel );
           fclose (fp);
           goto dalej;

Nie przypisuje mi poszczegolnych linijek pliku do okreslonych tablic. Wogole nie wiem, czy w fscanf moge stosowac cos takiego jak "%s\n". Chodzi oczywiscie zeby po przypisaniu lancucha do tablicy przeszedl do nastepnej linijki.

Link do komentarza
Udostępnij na innych stronach

No wiec wczytywanie dziala, ale nie dokladnie tak, jakbym sobie zyczyl :D Otoz wczytuje mi po kolei wartosc wszystkich linii w pliku do moich tablic zapisujac je dla jednej osoby w bazie. Ale powiedzmy, ze w pliku znajduja sie informacje o wiekszej ilosci osob (przykladowo, kilka linijek w pliku jest przewidzianych na jedna osobe, po czym zaczynaja sie, bez zadnych odstepow, informacje a temat nastepnej osoby). Nie wiem jak w moim programie okreslic ta liczbe osob znajdujacych sie w pliku. Jedyne co przychodzi mi do glowy to jakos zasygnalizowac programowi, ze wiekszej ilosci osob juz nie ma poprzez pokazanie, ze nastepna linia jest pusta. Nie mam pojecia jak to okreslic. Jak jakis geniusz mi to wyjasni to bede wielce wdzieczny. No a jak nie to zrobie wczytywanie dla jednej osoby i zostawie tak.

A tak przy okazji jeszcze, jest jakas fukcja w C odpowiedzialna za czesciowe czyszczenie ekranu? :D Bo by mi sie przydalo cos takiego.

Link do komentarza
Udostępnij na innych stronach

Jesli wszystkie pola (imie, nazwisko, etc) beda mialy te sama dlugosc (np uzupelniajac krotsze stringi jakimis specjalnymi znakami, jak '#'), zrobisz jeszcze, by wartosci inta byly zamieniane na chary i zapisywane do pliku, to pozniej mozesz sobie wczytywac z pliku znak po znaku.

ch = getc( input );
while( ch != EOF ) {
  printf( "%c", ch );
  ch = getc( input );
}

Ale najlepiej, jakbys zrobil znak oddzielajacy kolejne osoby w pliku i potem ddzielal substringi ;-)

Link do komentarza
Udostępnij na innych stronach



  • Kto przegląda   0 użytkowników

    • Brak zalogowanych użytkowników przeglądających tę stronę.
×
×
  • Utwórz nowe...