我在下面的文件“Magazzino.txt”中列出了几个类别的产品:
A451XX (codice prodotto)
CAT001 (codice categoria)
PASTA CONF. 1KG
100
99.0
A451XY (codice prodotto)
CAT002 (codice categoria)
MAGLIA LANA
25
6.70
A452XX (codice prodotto)
CAT001 (codice categoria)
SUGO
33
9.99
首先,我必须阅读文件并将所有产品复制到具有以下结构的列表中:
typedef struct {
char codP[C];
char codC[C];
char descr[D];
int num;
float costo;
} tipoBaseLista;
typedef struct nodoLista{
tipoBaseLista info;
struct nodoLista *next;
}prodotto;
typedef prodotto *listaP;
我需要在类别列表中复制此产品列表,以便每个类别都有一个子列表,其中包含属于特定类别的所有产品。这份清单的结构是:
typedef struct nodoCat{
char codC[C];
struct nodoCat *next;
listaP nodoP; //puntatore al sottonodo prodotto
}categoria;
typedef categoria *listaC;
这是完整的代码:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <malloc.h>
#define C 8
#define D 64
typedef struct {
char codP[C];
char codC[C];
char descr[D];
int num;
float costo;
} tipoBaseLista;
typedef struct nodoLista{
tipoBaseLista info;
struct nodoLista *next;
}prodotto;
typedef prodotto *listaP;
typedef struct nodoCat{
char codC[C];
struct nodoCat *next;
listaP nodoP;
}categoria;
typedef categoria *listaC;
int carica_lista(char fName[], listaP *l);
void inserimentoProd(listaP *l, tipoBaseLista p);
listaC trovaCategoria(listaC lc, char categoria[]);
void inserimentoSottolista(listaC lc, tipoBaseLista p, listaP *l);
int main() {
char filename[] = "Magazzino.txt";
listaP lista = NULL;
listaC listaCat = NULL;
tipoBaseLista prodotto;
printf("\nNumero prodotti caricati: %d\n", carica_lista(filename, &lista));
if(lista == NULL){
printf("\nLa lista dei prodotti è vuota!\n");
}
while(lista != NULL){
prodotto = lista->info;
if(listaCat == NULL){
listaCat = malloc(sizeof(categoria));
strcpy(listaCat->codC, prodotto.codC);
listaCat->next = NULL;
inserimentoSottolista(listaCat, prodotto, &lista);
}
else{
listaCat = trovaCategoria(listaCat, prodotto.codC);
if(listaCat != NULL){
inserimentoSottolista(listaCat, prodotto, &lista);
}
else{
listaCat = listaCat->next;
inserimentoSottolista(listaCat, prodotto, &lista);
}
}
lista = lista->next;
}
return 0;
system("PAUSE");
}
//read from file
int carica_lista(char fName[], listaP *l) {
tipoBaseLista prodotto;
int n = 0;
char buf[D] = {0};
char scarto[30];
FILE *f;
f = fopen(fName, "r");
if (f == NULL) {
printf("Non e' possibile aprire il file\n");
exit(1);
}
while (!feof(f)) {
fgets(buf, sizeof(buf), f);
sscanf(buf, "%s%s", prodotto.codP, scarto);
fgets(buf, sizeof(buf), f);
sscanf(buf, "%s%s", prodotto.codC, scarto);
fgets(buf, sizeof(buf), f);
strcpy(prodotto.descr, buf);
fgets(buf, sizeof(buf), f);
sscanf(buf, "%d", &prodotto.num);
fgets(buf, sizeof(buf), f);
sscanf(buf, "%f", &prodotto.costo);
inserimentoProd(l, prodotto);
n++;
}
fclose(f);
return n;
system("PAUSE");
}
//to insert product in the list
void inserimentoProd(listaP *l, tipoBaseLista p){
listaP pCorrente = NULL;
listaP pNodo;
listaP pPrec;
pNodo = malloc(sizeof(prodotto));
pNodo->info = p;
pNodo->next = NULL;
if (*l == NULL){
*l = pNodo;
}
else if(strcmp(p.codP, (*l)->info.codP) < 0){
pNodo->next = *l;
*l = pNodo;
(*l)->next = pNodo;
}
else{
pCorrente = *l;
while (pCorrente->next != NULL && strcmp(p.codP, pCorrente->info.codP) > 0){
pPrec = pCorrente;
pCorrente = pCorrente->next;
}
if(strcmp(p.codP, pCorrente->info.codP) < 0){
pNodo->next = pCorrente;
pPrec->next = pNodo;
}
else if(pCorrente->next == NULL) {
pCorrente->next = pNodo;
}
}
}
//To find the category node under which we insert the sublist
listaC trovaCategoria(listaC lc, char categoria[]){
listaC pCorrente = lc;
while(pCorrente != NULL){
if(strcmp(pCorrente->codC, categoria) == 0){
printf("\nCategoria già presente.\n");
return pCorrente;
}
pCorrente = pCorrente->next;
}
return(NULL);
}
//to insert the product in the head of sublist
void inserimentoSottolista(listaC lc, tipoBaseLista p, listaP *l){
printf("\nInserimento nella sottolista\n");
listaP prodotto = malloc(sizeof(struct nodoLista));
prodotto->info = p;
prodotto->next = *l;
*l = prodotto;
lc->nodoP = prodotto;
printf("\nInserimento effettuato\n");
}
“inserimentoSottolista”中必定存在导致程序崩溃的问题。它可能是什么?
答案 0 :(得分:1)
问题出在这里,在inserimentoSottolista中:
sizeof(prodotto)
您需要sizeof(struct nodoLista)
为之前声明的结构的大小,即prodotto
。但是,您对已初始化的变量的名称使用了相同的名称。在这种情况下,sizeof(prodotto)
中的sizeof(prodotto)
不是结构,而是变量。因此sizeof(listaP)
最终与sizeof(struct nodoLista)
相同,这只是指针的大小。它太小了,所以你没有分配足够的内存。
您可以通过更改变量名称来修复它,以便它不会屏蔽类型名称,或使用if __name__ == "__main__":
app = QtWidgets.QApplication(sys.argv)
MainWindow = QtWidgets.QMainWindow()
gui = MainMenuClass()
MainWindow.show()
sys.exit(app.exec_())
。