我正在读取一个Csv文件,每行包含3个数据。列表本身似乎填充了从Csv文件中获取的数据,因为如果我在Insert_list中使用printf,它会打印正确的内容,但是如果我打印列表,它仍会给我带来垃圾。
我认为问题出在insert_list中,因为这是搞砸列表的唯一方法,但我找不到那是。 我在列表中尝试了许多版本的输入并打印。我实际使用的似乎是最好的选择,因为至少如果我现在要求在insert_list中打印Lptr,它会为我提供正确的输入值。然后,如果我打印列表,则会给我垃圾。
程序中需要的结构。
typedef struct product {
int prod_code;
char prod_name[20];
int price;
int stockage;
}product;
typedef struct prod_list {
product product;
struct prod_list *next_ptr;
}prod_list;
typedef prod_list *Prod_ptr;
int threshold=10000;
功能:
void insert_list ( Prod_ptr *lptr , int code, char *name, int price);
void print_list( Prod_ptr *lptr);
主要:
int main (){
prod_list *lptr = NULL ;
FILE *file_ptr;
file_ptr= fopen( "semplice.csv" , "r");
if(file_ptr==NULL) {
printf("error program name");
return 1;
}
int code, price;
char name[20];
while (fscanf(file_ptr , "%d,%19[^,],%d", &code , name , &price) == 3) {
insert_list ( &lptr , code , name , price);
}
print_list(&lptr);
fclose(file_ptr);
return 0;
}
void insert_list(Prod_ptr *lptr, int code , char *name , int price) {
if(*lptr == NULL){
Prod_ptr newPtr = malloc(sizeof(prod_list));
if(newPtr != NULL){
newPtr->product.prod_code = code;
strcpy(newPtr->product.prod_name , name);
newPtr->product.price = price;
newPtr->product.stockage = rand() % (100001);
newPtr->next_ptr = NULL;
*lptr = newPtr;
}
else{
puts(" memoria esaurita");
}
}
else if ((*lptr)->product.prod_code >= code){
Prod_ptr newPtr = malloc(sizeof(prod_list));
if ( newPtr != NULL ) {
newPtr->product.prod_code = code;
strcpy(newPtr->product.prod_name , name);
newPtr->product.price = price;
newPtr->product.stockage = rand() % (100001);
newPtr->next_ptr = *lptr;
*lptr = newPtr;
}
else{
puts("mem esaurita");
}
}
else{
insert_list(&((*lptr)->next_ptr) , code , name, price);
}
}
void print_list( Prod_ptr *lptr){
Prod_ptr temp = lptr;
printf("Input Threshold:");
while((scanf("%d" , &threshold))!=1 && threshold > 0){
printf("error input");
scanf("%*[^\n]%*c");
}
if( temp == NULL){
puts("Error");
}
else {
for(temp = lptr; temp != NULL; temp = temp->next_ptr){
if( temp->product.stockage < threshold){
printf("Product code: %d\nProduct Name: %s\Product price: %d\Stockage: %d\n\n", temp->product.prod_code , temp->product.prod_name , temp->product.price , temp->product.stockage );
}
}
}
}
它可以编译,但是当print_list运行时,它给了我这种垃圾: 产品代码:11146320 产品名称: 产品价格:4199400 库存:0
但是,如果我在insert_list中打印lptr的值,它将为我提供正确的值。
csv文件包含:
4;Computer 3;950
12;Computer 4;1050
13;Computer 5;1150
24;Computer 6;1250
25;Computer 7;1350
27;Computer 8;1450
31;Computer 9;1550
32;Computer 10;1650
33;Telefono 1;103
35;Telefono 2;129
38;Telefono 3;155
答案 0 :(得分:1)
大多数问题来自使用typedef
指向prod_list
的指针。我删除了它,直接使用了prod_list *
。这使事情变得更容易编码和理解。查看我在代码中插入的注释。
#include "stdio.h"
#include "stdlib.h"
#include "string.h"
typedef struct product {
int prod_code;
char prod_name[20];
int price;
int stockage;
} product;
typedef struct prod_list {
product product;
struct prod_list *next_ptr;
} prod_list;
//typedef prod_list *Prod_ptr;
//void insert_list(Prod_ptr *lptr, int code, char *name, int price);
//void print_list(Prod_ptr *lptr);
void insert_list(prod_list **lptr, int code, char *name, int price);
void print_list(prod_list *lptr);
int threshold = 10000;
int main() {
prod_list *lptr = NULL;
FILE *file_ptr;
file_ptr = fopen("C:\\Users\\rbaron\\Documents\\Visual Studio 2015\\Projects\\ConsoleApplication3\\ConsoleApplication3\\Debug\\semplice.csv", "r");
if (file_ptr == NULL) {
printf("error program name");
return 1;
}
int code, price;
char name[20];
while (fscanf(file_ptr, "%d,%19[^,],%d", &code, name, &price) == 3) {
//insert_list(&lptr, code, name, price);
insert_list(&lptr, code, name, price);
}
//print_list(&lptr);
print_list(lptr);
fclose(file_ptr);
return 0;
}
//void insert_list(Prod_ptr *lptr, int code, char *name, int price) {
void insert_list(prod_list **lptr, int code, char *name, int price) {
if (*lptr == NULL) {
//Prod_ptr newPtr = malloc(sizeof(prod_list));
prod_list * newPtr = malloc(sizeof(prod_list));
if (newPtr != NULL) {
newPtr->product.prod_code = code;
strcpy(newPtr->product.prod_name, name);
newPtr->product.price = price;
newPtr->product.stockage = rand() % (100001);
newPtr->next_ptr = NULL;
*lptr = newPtr;
}
else {
puts(" memoria esaurita");
}
}
else if ((*lptr)->product.prod_code >= code) {
//Prod_ptr newPtr = malloc(sizeof(prod_list));
prod_list * newPtr = malloc(sizeof(prod_list));
if (newPtr != NULL) {
newPtr->product.prod_code = code;
strcpy(newPtr->product.prod_name, name);
newPtr->product.price = price;
newPtr->product.stockage = rand() % (100001);
newPtr->next_ptr = *lptr;
*lptr = newPtr;
}
else {
puts("mem esaurita");
}
}
else {
insert_list(&((*lptr)->next_ptr), code, name, price);
}
}
//void print_list(Prod_ptr *lptr) {
void print_list(prod_list *lptr) {
prod_list * temp = lptr;
// Not sure what this is doing???
//printf("Input Threshold:");
//while ((scanf("%d", &threshold)) != 1 && threshold > 0) {
// printf("error input");
// scanf("%*[^\n]%*c");
//}
if (temp == NULL) {
puts("Error");
}
else {
for (temp = lptr; temp != NULL; temp = temp->next_ptr) {
if (temp->product.stockage < threshold) {
//printf("Product code: %d\nProduct Name: %s\Product price: %d\Stockage: %d\n\n", temp->product.prod_code, temp->product.prod_name, temp->product.price, temp->product.stockage);
printf("Product code: %d\nProduct Name: %s\nProduct price: %d\nStockage: %d\n\n", temp->product.prod_code, temp->product.prod_name, temp->product.price, temp->product.stockage);
}
}
}
}
答案 1 :(得分:1)
insert函数中的指针指向指针是避免过多变量和条件所困扰的绝佳方法。和:以避免递归...
所以:使用它!
void insert_list(struct prodlist **pp, int code , char *name , int price)
{
struct prodlist *newp ;
// Advance pp, until it points to the pointer
// That *should* be pointing at the new entry
// That pointer *could* be NULL. In that case, we reached the end of the list;
for( ; *pp; pp = &(*pp)->next){
if((*pp)->product.prod_code >= code) break; // Found the place!
}
newp = malloc(sizeof *newp);
if(!newp ){
fprintf(stderr, "memoria esaurita\n");
return;
}
newp->product.prod_code = code;
strcpy(newp->product.prod_name , name);
newp->product.price = price;
newp->product.stockage = rand() % 100001;
newp->next = *pp;
*pp = newp;
}