Odczytywanie z pliku do struktury [C]

0

W ramach zaliczenia muszę napisać program realizujący kase fiskalną, mógłby mnie ktoś naprowadzić dlaczego nie chce wczytywać z pliku? W funkcji wczytaj program nie wchodzi w ogóle do pętli a według mnie powinien, specyfikatory przy while są chyba dobrze dobrane, nie wiem co leży, pozdrawiam :)

#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <locale.h>

struct produkt * wczytaj();
void zapisz(struct zakupione *kupno);
struct zakupione * trybkasy(struct produkt *zakupy);
void wyswietlprodukt(struct produkt *zakupy);
void wyswietlzakupy(struct zakupione *kupno);
void oczysc(struct zakupione * kupno);
struct produkt * przydzielpamiecproduktu(int val);
struct zakupione * przydzielpamieczakupiona(int val);
void oczysc1(struct produkt * produkty);

int main()
{
	struct produkt *nowy=NULL;
	struct zakupione *nowe=NULL;
	int spr,a;
	setlocale(LC_ALL,"polish");
	nowy=wczytaj();
	printf("Witaj!\nWybierz czynność:1.Wyświetlenie produktów\n2.Tryb kasy\n3.Jeśli chcesz wyjść wciśnij dowolną literę\nPodaj cyfrę:");
	while(scanf("%d",&spr)==1)
	{
		while(spr>3 || spr<1)
		{
		printf("Wprowadziłeś błędną cyfrę, wprowadź jeszcze raz!\n Podaj cyfrę:");
		a=scanf("%dwhile",&spr);
		}
		if(spr==1)
		{
			printf("Wybrałeś wyświetlenie!\n");
			wyswietlprodukt(nowy);
		}
		if(spr==2)
		{
			nowe=trybkasy(nowy);
			oczysc(nowe);
		}
		if(spr==3)
		{
			oczysc(nowe);
			oczysc1(nowy);
			printf("Żegnaj!");
			return 0;
		}
		printf("Witaj!\nWybierz czynność:1.Wyświetlenie produktów\n2.Tryb kasy\n3.Wyjście(lub podanie litery)\nPodaj cyfrę:");
	}
	if(nowe!=NULL)
		oczysc(nowe);
	if(nowy!=NULL)
		oczysc1(nowy);
	printf("Żegnaj!");
	return 0;
}
struct produkt
{
	char *nazwaproduktu;
	unsigned short *kodproduktu;
	float *cenaproduktu;
	char *oznaczenie;
	int ilosc;
};
struct zakupione
{
	char *nazwaproduktu;
	unsigned short *kodproduktu;
	float *cenaproduktu;
	float cena;
	float podatek;
	float reszta;
	int ilosc;
};
struct zakupione *trybkasy(struct produkt *zakupy)
{	
	struct zakupione *tmp=NULL;
	unsigned short kod;
	int a,i=0,j=0,spr,spr3,sztuka;
	float waga,cena,spr1,kwota;
	printf("Oto lista dostępnych artykułów");
	wyswietlprodukt(zakupy);
	for(;;)
	{	
		printf("Podaj kod produktu:\n");
		a=scanf("%hu",&kod);
		while(!a)
		{
			printf("Wpisałeś błędny kod! Podaj jeszcze raz!:\n");
			a=scanf("%hu",&kod);
		}
		for(i=0;i<=zakupy->ilosc;i++)
		{
			if(zakupy->kodproduktu[i]==kod)
			{
				printf("Podałeś poprawny kod!");
				break;
			}
			if(i==zakupy->ilosc)
			{
				printf("Podałeś błędny kod! Wprowadź jeszcze raz:\n");
				a=scanf("%hu",&kod);
				while(!a)
				{
					printf("Wpisałeś błędny kod! Podaj jeszcze raz!:\n");
					a=scanf("%hu",&kod);
				}
				i=0;
			}
		}
		tmp=przydzielpamieczakupiona(j);
		if(tmp==NULL)
		{
			printf("Błąd przydzielania pamięci!\n");
			return 0;
		}
		printf("Wybrałeś:%s\nCenaproduktu to:%f\n",zakupy->nazwaproduktu[i],zakupy->cenaproduktu[i]);
		if(zakupy->oznaczenie[i]=='S')
		{
			printf("Podaj ilość sztuk:\n");
			spr=scanf("%d",&sztuka);
			while(sztuka<0)
			{
				printf("Wprowadziłeś błędne dane!Podaj jeszcze raz:\n");
				spr=scanf("%d",&sztuka);
			}
			cena=sztuka*(zakupy->cenaproduktu[i]);
			tmp->cena=cena+(tmp->cena);
			tmp->nazwaproduktu[j]=zakupy->nazwaproduktu[i];
			tmp->cenaproduktu[j]=zakupy->cenaproduktu[i];
			tmp->kodproduktu[j]=zakupy->kodproduktu[i];
			j++;
		}
		if(zakupy->oznaczenie[i]=='W')
		{
			printf("Podaj wagę:\n");
			spr1=scanf("%f",&waga);
			while(waga<0)
			{
				printf("Wprowadziłeś błędne dane!Podaj jeszcze raz:\n");
				spr=scanf("%f",&waga);
			}
			cena=waga*(zakupy->cenaproduktu[i]);
			tmp->cena=cena+(tmp->cena);
			tmp->nazwaproduktu[j]=zakupy->nazwaproduktu[i];
			tmp->cenaproduktu[j]=zakupy->cenaproduktu[i];
			tmp->kodproduktu[j]=zakupy->kodproduktu[i];
			j++;
		}
		printf("Aby wybrać kolejny produkt wciśnij dowolną cyfrę, aby przerwać kupowanie wciśnij dowolną literę:\n");
		spr=scanf("%d",&spr3);
		if(!spr)
			break;
	}
	printf("Podaj kwotę otrzymaną od klienta w celu wydania reszty:\n");
	spr=scanf("%f",&kwota);
	while(spr==0 || kwota<0 || kwota-(tmp->cena)<0) // jeszcze wycofanie?
	{
		printf("Kwota została błędnie wprowadzona!Wprowadź jeszcze raz!");
		spr=scanf("%f",&kwota);
	}
	tmp->reszta=kwota-(tmp->cena);
	tmp->podatek=0.23*(tmp->cena);
	tmp->ilosc=j;
	wyswietlzakupy(tmp);
	zapisz(tmp);
	return tmp;
}
struct zakupione *przydzielpamieczakupiona(int val)
{
	struct zakupione *kupno;
	char *prt;
	float *prt1;
	unsigned short *prt2;
	kupno=(struct zakupione *)calloc(1,sizeof(struct zakupione));
	if(kupno==NULL)
	{
		printf("Błąd przydzielania pamięci!\n");
		return 0;
	}
	prt=(char*)realloc((kupno->nazwaproduktu),(val+1)*sizeof(char));
	if(prt==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(kupno);
		return 0;
	}
	prt1=(float*)realloc((kupno->cenaproduktu),(val+1)*sizeof(float));
	if(prt1==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(prt);
		free(kupno);
		return 0;
	}
	prt2=(unsigned short*)realloc((kupno->kodproduktu),(val+1)*sizeof(unsigned short));
	if(prt2==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(prt);
		free(prt1);
		free(kupno);
		return 0;
	}
	kupno->nazwaproduktu=prt;
	kupno->cenaproduktu=prt1;
	kupno->kodproduktu=prt2;
	return(kupno);
}
struct produkt *przydzielpamiecproduktu(int val)
{
	struct produkt *kupno;
	char *prt1,*prt2;
	float *prt3;
	unsigned short *prt4;
	kupno=(struct produkt *)calloc(1,sizeof(struct produkt));
	if(kupno==NULL)
	{
		printf("Błąd przydzielania pamięci!\n");
		return 0;
	}
	prt1=(char*)realloc((kupno->nazwaproduktu),(val+1)*sizeof(char));
	if(prt1==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(kupno);
		return 0;
	}
	prt2=(char*)realloc((kupno->oznaczenie),(val+1)*sizeof(char));
	if(prt2==NULL)
	{
		printf("Błąd przedzielania pamięci!");
		free(prt1);
		free(kupno);
		return 0;
	}
	prt3=(float*)realloc((kupno->cenaproduktu),(val+1)*sizeof(float));
	if(prt3==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(prt1);
		free(prt2);
		free(kupno);
		return 0;
	}
	prt4=(unsigned short*)realloc((kupno->kodproduktu),(val+1)*sizeof(unsigned short));
	if(prt4==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(prt1);
		free(prt2);
		free(prt3);
		free(kupno);
		return 0;
	}
	kupno->nazwaproduktu=prt1;
	kupno->oznaczenie=prt2;
	kupno->cenaproduktu=prt3;
	kupno->kodproduktu=prt4;
	return(kupno);
}
struct produkt *wczytaj()
{
	struct produkt *tmp=NULL;
	int mem_size=0,i=0;
	FILE *plik;
	plik=fopen("produkty.csv","rt");
	if(plik==NULL)
	{
		printf("Błąd otwarcia pliku!\n");
		return 0;
	}
	printf("Przydzielam pamięć!");
	tmp=przydzielpamiecproduktu(mem_size);
	printf("Przydzieliłem!\n");
	if(tmp==NULL)
	{
		printf("Pamięć błędnie przydzielona!");
		fclose(plik);
		oczysc1(tmp);
		return 0;
	}
	mem_size++;
	while((fscanf(plik,"%f;%hu;%c;%s\n",&tmp->cenaproduktu[i],&tmp->kodproduktu[i],&tmp->oznaczenie[i],&tmp->nazwaproduktu[i]))==4)
	{	
		printf("Czy byłem w while?");
		if(tmp->oznaczenie[i]!='S' || tmp->oznaczenie[i]!='W')
		{
			printf("Błędne oznaczenie ilości/wagi!\n");
			return 0; 
		}
		tmp=przydzielpamiecproduktu(mem_size);
		if(tmp==NULL)
		{
			printf("Pamięć błędnie przydzielona!\n");
			fclose(plik);
			oczysc1(tmp);
			return 0;
		}
		mem_size++;
		i++;
	}
	printf("Pomijam\n");
	tmp->ilosc=(i);
	fclose(plik);
	printf("Produkty zostały pomyślnie wczytane!\nIlość odczytanych produktów wynosi %d!",tmp->ilosc);
	return(tmp);
}
void zapisz(struct zakupione *kupno)
{
	 FILE *plik;
	 int i=0;
	 plik=fopen("zakupione.csv","wt");
	 if(plik==NULL)
	 {
		 printf("Błąd otwarcia pliku!\n");
		 return;
	 }
	 for(i=0;i<(kupno->ilosc);i++)
		 fprintf(plik,"%s;%hu;%f\n",kupno->nazwaproduktu[i],kupno->kodproduktu[i],kupno->cenaproduktu[i]);
	 fprintf(plik,"%f\n %f\n %f\n",kupno->cena,kupno->reszta,kupno->podatek);
	 printf("Paragon został pomyślnie zapisany!\n");
	 fclose(plik);
}
void wyswietlprodukt(struct produkt*zakupy)
{  
	int i;
	printf("%f",zakupy->cenaproduktu[2]);
	printf("Oto lista produktów:\n");
	for(i=0;i<(zakupy->ilosc);i++)
	{	
		printf("%f",zakupy->cenaproduktu[i]);
		printf("%s %hu %f\n",zakupy->nazwaproduktu[i],zakupy->kodproduktu[i],zakupy->cenaproduktu[i]);	
	}
	printf("Produkty zostały wyświetlone!\n");
}
void wyswietlzakupy(struct zakupione *kupno)
{
	int i;
	printf("Oto paragon:\n");
	for(i=0;i<(kupno->ilosc);i++)
		printf("%s %hu %f\n",kupno->nazwaproduktu[i],kupno->kodproduktu[i],kupno->cenaproduktu[i]);
	printf("Cena:%fzł\nPodatek:%fzł\nReszta:%fzł\n",kupno->cena,kupno->podatek,kupno->reszta);
	printf("Paragon został wyświetlony\n");
}
void oczysc(struct zakupione *kupno)
{
	if(kupno==NULL)
		return;
	
	
		if(kupno->nazwaproduktu!=NULL)
			free(kupno->nazwaproduktu);
		if(kupno->cenaproduktu!=NULL)
			free(kupno->cenaproduktu);
		if(kupno->kodproduktu!=NULL)
			free(kupno->kodproduktu);
		free(kupno);
	
}
void oczysc1(struct produkt *produkty)
{
	if(produkty==NULL)
		return;
		
		if(produkty->nazwaproduktu!=NULL)
			free(produkty->nazwaproduktu);
		if(produkty->cenaproduktu!=NULL)
			free(produkty->cenaproduktu);
		if(produkty->kodproduktu!=NULL)
			free(produkty->kodproduktu);
		if(produkty->oznaczenie!=NULL);
			free(produkty->oznaczenie);
		free(produkty);
	
}
 
0

Wygląda na to, że w while jest jednak coś nie tak. Po usunięciu kilku rzeczy weszło mi do pętli. Może masz też inaczej zapisane dane w pliku niż format podczas czytania?

0

W czterech kolumnach kolejno mam wpisane Makaron 325 16,89 W - czyli zgodnie łańcuch, unsigned short, float i char czyli oznacznie

0

Średniki aby przechodzić między kolejnymi kolumnami?

0

W pliku masz zapisane:
Makaron;325;16,89;W
W związku z czym przy odczycie masz cały wiersz wczytany wg formatu %s
Zapisuj wg formatu: printf("%u %f %c %s\n"...
Wczytuj wg formatu: scanf(" %u %f %c "... plus fgtets

0

Czyli jak mam średniki to on traktuje całe wiersz jako jeden łańcuch? Fgets czyta dopóki nie natrafi na znak końca lini, jak to z nim rozwiązać żeby rozróżniał moje cztery wartości i przypisywał je od razu do moich tablic?
Sorry Panowie ale człowiek sie uczy całe życie i wolę się dopytać i wyjść na głupiego niż sam dochodzić do tego przez 30 minut :)

0
void read_to_character(char* buffer, char character) {
    char c;
    int i=0;
    while((c = getchar()) != character) {
        buffer[i++] = c;
    }
    buffer[i] = 0;
}

http://ideone.com/OzYrgV

0

Panowie szczerze to trochę nie nadążam za wami, w programie poprawiłem jeszcze parę rzeczy(uaktualniłem program u góry), które leżały ale dalej pozostaje problem z wczytaniem, na laboratorium odczytywaliśmy z pliku .csv przy pomocy średników ale to były wartości typu float, a tutaj jak sobie sprawdzałem to faktycznie on całą linijkę wczytuje do łańcucha od razu a gdy przychodzi czas na resztę while się wysypuje i dalej nie idzie. Jak to ruszyć? Tutaj kolega wyżej wrzucił mi funkcje, ale jak ją ugryźć(jeszcze sie uczę także proszę o wyrozumienie).. Prosiłbym o pomoc bo jutro chciałbym oddać ten program bo jednak reszta egzaminów atakuje :)

0
Bra5i napisał(a):

Jak to ruszyć?
Normalnie użyj tej funkcji.

0
_13th_Dragon napisał(a):
Bra5i napisał(a):

Jak to ruszyć?
Normalnie użyj tej funkcji.

no ale nie rozumiem, dlatego pytam. Getchar odczyta cały łańcuch i wpisze go do tablicy po czym jak trafi na średnik wyjdzie z funkcji, następnie wartości unsigned short, float i char odczytuję normalnie podając średnik? Gdy odczytam ostatnią wartość w tej linijce czyli &char->oznaczenie znowu wywołuję funkcję odczytując do momentu średnika(czyli w pętli) ?

0

Masz dwa warianty:

  1. wg tego co ja zaproponowałem: przenieś napis na koniec i nie ma problemów
  2. wg tego co @n0name_l zaproponował, napis wczytujesz funkcją resztę normalnie scanf'em
0

Zmieniłem wczytaj w ten sposób i dalej nie czyta..

 struct produkt *wczytaj()
{
	struct produkt *tmp=NULL;
	char *result;
	int mem_size=0,i=0;
	FILE *plik;
	plik=fopen("produkty.csv","rt");
	if(plik==NULL)
	{
		printf("Błąd otwarcia pliku!\n");
		return 0;
	}
	printf("Przydzielam pamięć!\n");
	tmp=przydzielpamiecproduktu(mem_size);
	printf("Przydzieliłem!\n");
	if(tmp==NULL)
	{
		printf("Pamięć błędnie przydzielona!");
		fclose(plik);
		oczysc1(tmp);
		return 0;
	}
	mem_size++;
	while((fscanf(plik,"%f %hu %c",&tmp->cenaproduktu[i],&tmp->kodproduktu[i],&tmp->oznaczenie[i]))==3)
	{
		result=fgets(tmp->nazwaproduktu,sizeof(tmp->nazwaproduktu),plik);
		if(result==NULL)
		{
			printf("Błąd odczytu!\n");
			return 0;
		}
		if(tmp->oznaczenie[i]!='S' || tmp->oznaczenie[i]!='W')
		{
			printf("Błędne oznaczenie ilości/wagi!\n");
			return 0; 
		}
		if(feof(plik)==0)
		{
			printf("Koniec pliku!");
			break;
		}
		tmp=przydzielpamiecproduktu(mem_size);
		if(tmp==NULL)
		{
			printf("Pamięć błędnie przydzielona!\n");
			fclose(plik);
			oczysc1(tmp);
			return 0;
		}
		mem_size++;
		i++;
	}
	printf("Pomijam\n");
	tmp->ilosc=(i);
	fclose(plik);
	printf("Produkty zostały pomyślnie wczytane!\nIlość odczytanych produktów wynosi %d!",tmp->ilosc);
	return(tmp);
}
}
0

Poradziłem sobie już z tym zagadnieniem, teraz już mi wszystko czyta, ale jak to bywa.. code & fix..
Mój kolejny problem leży w tym,że z próbowałem zapisywać nazwy do tablicy znaków, więc teraz walczę z tablicą łańcuchów, mam ją dwuwymiarową, i deklaruję funkcję w ten sposób, co wy na to:

struct produkt *przydzielpamiecproduktu(struct produkt *kupno,int val,float cena,unsigned short kod,int oznaczenie, char *buff)
{	
	char **prt1;
	int *prt2;
	float *prt3;
	unsigned short *prt4;
	int i,size;
	size=strlen(buff);
	if(kupno==NULL)
	{
		kupno=(struct produkt *)calloc(1,sizeof(struct produkt));
		if(kupno==NULL)
		{
			printf("Błąd przydzielania pamięci!\n");
			return 0;
		}
	}
	prt1=(char**)realloc((kupno->nazwaproduktu),(val+1)*sizeof(char*));
	if(prt1==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(kupno);
		return 0;
	}
	for(i=0;i<size;i++)
	{
		prt1[i]=(char*)realloc((kupno->nazwaproduktu),(size)*sizeof(char)));
		if(prt1[i]==NULL)
		{
			printf("Błąd przydzielania pamięci!\n");
			free(kupno);
			return 0;
		}
	}
	prt2=(int*)realloc((kupno->oznaczenie),(val+1)*sizeof(int));
	if(prt2==NULL)
	{
		printf("Błąd przedzielania pamięci!");
		free(prt1);
		free(kupno);
		return 0;
	}
	prt3=(float*)realloc((kupno->cenaproduktu),(val+1)*sizeof(float));
	if(prt3==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(prt1);
		free(prt2);
		free(kupno);
		return 0;
	}
	prt4=(unsigned short*)realloc((kupno->kodproduktu),(val+1)*sizeof(unsigned short));
	if(prt4==NULL)
	{
		printf("Błąd przydzielania pamięci!");
		free(prt1);
		free(prt2);
		free(prt3);
		free(kupno);
		return 0;
	}
	kupno->nazwaproduktu=prt1;
	for(i=0;i<size;i++)
	{
		kupno->nazwaproduktu[val][i]=buff[i];
	}
	kupno->oznaczenie=prt2;
	kupno->oznaczenie[val]=oznaczenie;
	kupno->cenaproduktu=prt3;
	kupno->cenaproduktu[val]=cena;
	kupno->kodproduktu=prt4;
	kupno->kodproduktu[val]=kod;
	return(kupno);
}
 
1

Może przerób całość dopóki nie zabrnąłeś zbyt daleko.
Twoja struktura powinna wyglądać następująco:

struct produkt
  {
   char *nazwa;
   int oznaczenie;
   unsigned short kod;
   float cena;
   int ilosc;
  };

struct produkty
  {
   struct produkt *tablica;
   unsigned ilosc;
  };

void przydzielpamiecproduktu(struct produkty *sklep,int ilosc,float cena,unsigned short kod,int oznaczenie,const char *nazwa)
  {
   sklep->tablica=(struct produkt *)realloc(sklep->tablica,sklep->ilosc*sizeof(struct produkt));
   sklep->tablica[sklep->ilosc].nazwa=strdup(nazwa);
   sklep->tablica[sklep->ilosc].ilosc=ilosc;
   sklep->tablica[sklep->ilosc].cena=cena;
   sklep->tablica[sklep->ilosc].kod=kod;
   sklep->tablica[sklep->ilosc].oznaczenie=oznaczenie;
   ++sklep->ilosc;
  }

Zauważ o ile jest prostsze.

0

Dzięki wielkie! Nie wpadłem na to, czlowiek się uczy całe życie!:)

0

No więc tak, sprawdzałem debugger'em i problem leży w funkcjach oczyszczających bo nie robią tego jak powinny, mógłby ktoś skontrolować jak to powinno wyglądać żeby z pamięcią się cuda nie działy? z góry dziękuje!

 #define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <locale.h>

struct produkt
  {
   char *nazwa;
   int oznaczenie;
   unsigned short kod;
   float cena;
  };
struct produkty
  {
   struct produkt *tablica;
   int ilosc;
  };
struct paragon
{
	char *nazwap;
	unsigned short kodp;
	float cenap;
	int sztuka;
	float waga;
	int oznaczenie;
};
struct calyparagon
{
	struct paragon *tab;
	int iloscp;
	float cena_end;
	float podatek;
	float reszta;
};
void zapisz(struct calyparagon *paragon);
struct produkty *przydzielpamiecproduktu(struct produkty *sklep,int mem_size,float cena,unsigned short kod,int oznaczenie,const char *nazwa);
struct produkty *wczytaj();
void wyswietl(struct produkty *sklep);
void wyswietl1(struct calyparagon *paragon);
struct calyparagon *kasa(struct produkty *sklep);
struct calyparagon *przydzielpamiec(struct calyparagon *zakupione,struct produkty *sklep,int val,int mem_size);
void oczysc(struct produkty *sklep);
void oczysc1(struct calyparagon *zakupione);

int main()
{
	struct produkty *listaproduktow=NULL;	
	struct calyparagon *listazakupionych=NULL;
	setlocale(LC_ALL,"polish");
	printf("Witaj w kasie!\n");
	listaproduktow=wczytaj();
	listazakupionych = kasa(listaproduktow);
	zapisz(listazakupionych);
	wyswietl1(listazakupionych);
	printf("Przeszedłem przez wyświetl\n");
	oczysc(listaproduktow);
	printf("Przeszedłem przez oczyść\n");
	oczysc1(listazakupionych);
	system("PAUSE");
	return 0;
}
struct produkty *wczytaj()
{
	struct produkty *sklep=NULL;
	float cena;
	int oznaczenie,i=0,mem_size=0;
	unsigned short kod;
	char nazwa[100];
	FILE *plik;
    plik=fopen("produkty.txt","rt");
    if(plik==NULL)
    {
		printf("Błąd otwarcia pliku!\n");
        return 0;
    }
	while((fscanf(plik,"%f%hu%d%s",&cena,&kod,&oznaczenie,&nazwa))==4)
	{
		if(oznaczenie!=1 && oznaczenie!=2)
        {
			printf("Błędne oznacznie!\n");
            return 0;
        }
		sklep=przydzielpamiecproduktu(sklep,mem_size,cena,kod,oznaczenie,nazwa);
		if(sklep==NULL)
		{
			printf("Pamięć błędnie przydzielona!\n");
			fclose(plik);
			return 0;
		}
		mem_size++;
		i++;
	}
	sklep->ilosc=i;
	fclose(plik);
	printf("Liczba produktów dostępnym w bazie:%d\n",i);
	return (sklep);
}
void zapisz(struct calyparagon *zakupione)
{
	 FILE *plik;
	 int i=0;
	 plik=fopen("paragon.txt","wt");
	 if(plik==NULL)
	 {
		 printf("Błąd otwarcia pliku!\n");
		 return;
	 }
	 for(i=0;i<=(zakupione->iloscp);i++)
	 {
		 if(i==0)
			 fprintf(plik,("Nazwa produktu Kod Produktu Cena Produktu Waga/Ilość\n"));
		 if(zakupione->tab[i].oznaczenie==1)
			 fprintf(plik,("%s %hu %f %d\n"),zakupione->tab[i].nazwap,zakupione->tab[i].kodp,zakupione->tab[i].cenap,zakupione->tab[i].sztuka);
		 else
			 fprintf(plik,("%s %hu %f %f\n"),zakupione->tab[i].nazwap,zakupione->tab[i].kodp,zakupione->tab[i].cenap,zakupione->tab[i].waga);
	 }
	 fprintf(plik,"Cena:%f Reszta:%f Podatek:%f",zakupione->cena_end,zakupione->reszta,zakupione->podatek);
	 printf("Paragon został pomyślnie zapisany!\n");
	 fclose(plik);
}
struct produkty *przydzielpamiecproduktu(struct produkty *sklep,int mem_size,float cena,unsigned short kod,int oznaczenie, const char *nazwa)
{
	if(sklep==NULL)
	{
		sklep=(struct produkty *)calloc(1,sizeof(struct produkty));
		if(sklep==NULL)
		{
			printf("Błąd przydzielania pamięci!\n");
			return 0;
		}
	}
	sklep->tablica=(struct produkt *)realloc(sklep->tablica,(mem_size+1)*sizeof(struct produkt));
	if(sklep->tablica==NULL)
	{
		printf("Błąd przydzielania pamięci!\n");
		return 0;
	}
    sklep->tablica[mem_size].nazwa=strdup(nazwa);
    sklep->tablica[mem_size].cena=cena;
    sklep->tablica[mem_size].kod=kod;
    sklep->tablica[mem_size].oznaczenie=oznaczenie;
	sklep->ilosc=mem_size;
	return(sklep);
}
void wyswietl(struct produkty *sklep)
{
	int i;
	printf("Produkty:\n");
	if(sklep==NULL)
	{
		printf("Nie ma co wyświetlać!\n");
		return;
	}
	for(i=0;i<sklep->ilosc;i++)
		printf("Nazwa produktu:%s,Cena produktu: %.2f,Kod produktu: %d\n",sklep->tablica[i].nazwa,sklep->tablica[i].cena,sklep->tablica[i].kod);
	printf("Produkty zostały wyświetlone!\n");
}
void wyswietl1(struct calyparagon *zakupione)
{
	int i;
	printf("Paragon:\n");
	if(zakupione==NULL)
	{
		printf("Nie ma co wyświetlać");
		return;
	}
	for(i=0;i<=zakupione->iloscp;i++)
	{
		if(zakupione->tab[i].oznaczenie==1)
			printf("Nazwa produktu:%s,Cena produktu: %.2f,Kod produktu: %d,Ilość sztuk:%d\n",zakupione->tab[i].nazwap,zakupione->tab[i].cenap,zakupione->tab[i].kodp,zakupione->tab[i].sztuka);
		else
			printf("Nazwa produktu:%s,Cena produktu: %.2f,Kod produktu: %d,Waga:%.2f\n",zakupione->tab[i].nazwap,zakupione->tab[i].cenap,zakupione->tab[i].kodp,zakupione->tab[i].waga);
	}
	printf("Do zapłaty:%f\nReszta:%f\nPodatek:%f\n",zakupione->cena_end,zakupione->reszta,zakupione->podatek);
	printf("Produkty zostały wyświetlone!\n");
}
struct calyparagon *kasa(struct produkty *sklep)
{
	struct calyparagon *zakupione=NULL;
	unsigned short kod;
	int i,j=0,spr,spr1,spr2,spr3,sztuka;
	float waga,cenaall=0,kwota;
	wyswietl(sklep);
	printf("Podaj kod wybranego produktu:\n");
	spr=scanf("%hu",&kod);
	for(;;)
	{
		for(i=0;i<=sklep->ilosc;i++)
		{
			while(!spr)
			{
				printf("Podałeś błędny kod!Podaj raz jeszcze:\n");
				spr=scanf("%hu",&kod);
			}
			if(i==sklep->ilosc)
			{
				printf("Podałeś błędny kod! Podaj raz jeszcze:\n");
				spr=scanf("%hu",&kod);
				i=0;
			}
			if(sklep->tablica[i].kod==kod)
			{
				printf("Wybrany przez Ciebie produkt to: %s, jego cena to %f\n",sklep->tablica[i].nazwa,sklep->tablica[i].cena);
				if(sklep->tablica[i].oznaczenie==1)
				{
					printf("Podaj ilość sztuk towaru:\n");
					spr1=scanf("%d",&sztuka);
					while(!spr1 || sztuka<0)
					{
						printf("Podałeś błędną ilość sztuk towaru!Podaj jeszcze raz:\n");
						spr1=scanf("%d",&sztuka);
					}
					fflush(stdin);
					cenaall=cenaall+sztuka*(sklep->tablica[i].cena);
					zakupione=przydzielpamiec(zakupione,sklep,i,j);
					zakupione->tab[j].sztuka=sztuka;
					zakupione->tab[j].waga=0;
					zakupione->tab[j].oznaczenie=sklep->tablica[i].oznaczenie;
					j++;
				}
				else
				{
					printf("Podaj wagę towaru:\n");
					spr2=scanf("%f",&waga);
					while(!spr2 || waga<0)
					{
						printf("Podałeś błędną wagę towaru!Podaj jeszcze raz:\n");
						spr=scanf("%f",&waga);
					}
					cenaall=cenaall+waga*(sklep->tablica[i].cena);
					zakupione=przydzielpamiec(zakupione,sklep,i,j);
					zakupione->tab[j].waga=waga;
					zakupione->tab[j].sztuka=0;
					zakupione->tab[j].oznaczenie=sklep->tablica[i].oznaczenie;
					j++;
				}
				break;
			}
		}
		printf("Podaj kod kolejnego artykułu(podanie dowolnej litery spowoduje przerwanie kupowania):\n");
		spr=scanf("%hu",&kod);
		if(!spr)
			break;
	}
	zakupione->cena_end=cenaall;
	zakupione->podatek=0.23*cenaall;
	printf("Kwota do zapłaty:%f\n",zakupione->cena_end);
	printf("Podaj kwotę otrzymaną od klienta:\n");
	fflush(stdin);
	spr3=scanf("%f",&kwota);
	while(!spr3 || kwota<zakupione->cena_end)
	{
		printf("Podałeś złą kwotę!");
		spr3=scanf("%f",&kwota);
	}
	zakupione->reszta=kwota-zakupione->cena_end;
	printf("Reszta wynosi:%f\n",zakupione->reszta);
	return(zakupione);
}		
struct calyparagon *przydzielpamiec(struct calyparagon *zakupione,struct produkty *sklep,int val,int mem_size)
{
	if(zakupione==NULL)
	{
		zakupione=(struct calyparagon *)calloc(1,sizeof(struct calyparagon));
		if(zakupione==NULL)
		{
			printf("Błąd przydzielania pamięci!\n");
			return 0;
		}
	}
	zakupione->tab=(struct paragon *)realloc(zakupione->tab,(mem_size+1)*sizeof(struct paragon));
	if(zakupione->tab==NULL)
	{
		printf("Błąd przydzielania pamięci!\n");
		free(zakupione);
		return 0;
	}
	zakupione->tab[mem_size].nazwap=sklep->tablica[val].nazwa;
	zakupione->tab[mem_size].cenap=sklep->tablica[val].cena;
	zakupione->tab[mem_size].kodp=sklep->tablica[val].kod;
	zakupione->iloscp=mem_size;
	return(zakupione);
}
void oczysc(struct produkty *sklep)
{
	if(sklep==NULL)
		return;
	if(sklep->tablica!=NULL)
	{
		if(sklep->tablica->nazwa)
			free(sklep->tablica->nazwa);
		free(sklep->tablica);
	}
	free(sklep);	
}
void oczysc1(struct calyparagon *zakupione)
{	
	if(zakupione==NULL)
		return;
	if(zakupione->tab!=NULL)
	{
		if(zakupione->tab->nazwap)
			free(zakupione->tab->nazwap);
		free(zakupione->tab);
	}
	free(zakupione);
}
		



		


0

Zacznij od uproszczenia kodu.
Zauważ że paragon to lista produktów więc niczym się nie powinien różnić od listy produktów, pola cena końcowa, podatek i reszta mogą zostać puste, albo też wypełniane podczas sprzedaży.

0

Objawia się takim komunikatem na koniec:

"Windows has triggered a breakpoint in Newww.exe.

This may be due to a corruption of the heap, which indicates a bug in Newww.exe or any of the DLLs it has loaded.

This may also be due to the user pressing F12 while Newww.exe has focus.

The output window may have more diagnostic information."
0

Problem leżał ze zwalnianiem większej ilości pamięci niż była zadeklarowana

Można usunąć :)

1 użytkowników online, w tym zalogowanych: 0, gości: 1