【发布时间】:2021-07-22 14:48:24
【问题描述】:
我编写了一个程序,它利用结构数组来维护一种具有不同选项的“数据库”程序,可用于操作“数据库”。
程序有4种操作模式,如果用户进入:
-
'i'数据可以插入到“数据库”中。 -
's'在“数据库”中搜索具有项目部件号的部件。 -
'u'根据商品的部件号更新数据库中的某些内容。 -
'p'打印整个“数据库”。
这是由 3 个文件组成的代码:
database.h:
#ifndef DATABASE
#define DATABASE
struct db
{
int part_number;
char *part_name;
int part_quantity;
};
extern struct db database[50];
extern void insert(int i);
extern int search(int i);
extern int update(int i);
extern int print(int i);
#endif
database.c
#include <string.h>
#include <stdio.h>
#include "database.h"
struct db database[50];
void insert(int i)
{
char name_of_part[21], c;
printf("%p\n", &database[i].part_name);
printf("\n");
printf("Enter a part number: ");
scanf("%d", &database[i].part_number);
while((c = getchar()) != '\n' && c != EOF); // flush stdin
printf("Enter a part name: ");
fgets(name_of_part, 20, stdin);
printf("Enter quantity of part: ");
scanf("%d", &database[i].part_quantity);
database[i].part_name = name_of_part;
printf("\n");
}
int search(int i)
{
int input;
printf("\n");
printf("Enter a part number: ");
scanf("%d", &input);
for (int j = 0; j <= i; j++)
{
if (database[j].part_number == input)
{
printf("Part name: %s\n", database[j].part_name);
printf("Quantity on hand: %d\n", database[j].part_quantity);
return 0;
}
}
printf("Part not found.\n");
}
int update(int i)
{
int input, quantity;
printf("\n");
printf("Enter part number: ");
scanf("%d", &input);
for (int j = 0; j <= i; j++)
{
if (database[j].part_number == input)
{
printf("Enter part quantity: ");
scanf("%d", &quantity);
database[j].part_quantity = quantity;
return 0;
}
}
printf("Part number not found.");
}
int print(int i)
{
for (int j = 0; j < i; j++)
{
printf("Part number: %d\n Part name: %s\n Part quantity: %d\n", database[j].part_number, database[j].part_name,database[j].part_quantity);
}
}
main.c
#include <stdio.h>
#include <string.h>
#include "database.h"
int main()
{
int i = 0;
char code;
while (1)
{
printf("Enter a function code: ");
scanf(" %c", &code);
switch (code)
{
case 'i':
insert(i);
i += 1;
break;
case 's':
search(i);
break;
case 'u':
update(i);
break;
case 'p':
print(i);
break;
}
}
return 0;
}
我遇到的问题是,当我插入“数据库”时,每个结构中的名称都会被覆盖。例如:
Enter a function code: i
Enter a part number: 111
Enter a part name: 111
Enter quantity of part: 111
Enter a function code: i
Enter a part number: 222
Enter a part name: 222
Enter quantity of part: 222
Enter a function code: p
Part number: 111
Part name: 222
Part quantity: 111
Part number: 222
Part name: 222
Part quantity: 222
Enter a function code:
正如您首先看到的,我在“数据库”中插入了一些新内容,记下“部件名称”,即“111”。
接下来我将其他内容插入数据库 这次“零件名称”是“222”。
最后我打印了整个“数据库”,我感到困惑的是为什么零件名称现在重叠了。但这是为什么呢?所有其他成员,例如 part_number 和 part_quantity 在两个插入操作中都保持不变,那么为什么 char *part_name 保持不变?我该如何解决这个问题?
【问题讨论】:
-
database[i].part_name = name_of_part是问题所在:name_of_part是一个 local 变量,一旦函数返回,它的生命周期就会结束,导致指针无效。 -
database[i].part_name = name_of_part;这是非法的。name_of_part是该函数中的一个局部非静态变量。当您离开该功能时,它的生命周期就结束了。这会导致未定义的行为。 -
您需要在each结构元素中分配内存,并将输入的字符串数据复制到它。
strdup函数可以同时执行这两种操作,但是当您删除/删除该元素时,您需要free()每个元素的part_name。
标签: c struct structure-of-arrays