Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ruby-on-rails-3/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C-带结构数组的realloc_C - Fatal编程技术网

C-带结构数组的realloc

C-带结构数组的realloc,c,C,我正在做一个结构数组来动态分配一个产品列表,但这只工作了几次(3~5次),然后我得到了这个错误 “./测试”中出现错误:realloc():下一个大小无效:0x00005BC0B44F260* 这是我的代码,这是大学工作的一部分 #include <stdio.h> #include <stdlib.h> typedef struct { int cod; float price; } Product; int main () { FILE

我正在做一个结构数组来动态分配一个产品列表,但这只工作了几次(3~5次),然后我得到了这个错误

“./测试”中出现错误:realloc():下一个大小无效:0x00005BC0B44F260*

这是我的代码,这是大学工作的一部分

#include <stdio.h>
#include <stdlib.h>

typedef struct {
    int cod;
    float price;
} Product;

int main () {

    FILE *fp;

    fp = fopen("products.txt", "r+");

    if(fp == NULL)
        fopen("products.txt", "w+");

    int control = 1;
    int choice;
    int tam = 0;
    int i;
    Product *p1;

    p1 = malloc(sizeof(Product));

    while(fread(&p1[0], sizeof(Product), 1, fp) != NULL){
        tam++;
    }

    if(tam > 1){
        rewind(fp);

        p1 = malloc((tam) * sizeof(*p1));

        for (int i = 0; i < tam; i++){
            fread(&p1[i], sizeof(Product), 1, fp);
        }
    }

    rewind(fp);

    do {
        printf("1 - Add product\n2 - Show all products\n3 - Exit\n-> ");
        scanf(" %d", &choice);

        switch (choice) {
            case 1:
                 if (tam == 0) {
                    //p1 = malloc(sizeof(Product));
                    printf("Digit the product code: ");
                    scanf(" %d", &p1[tam].cod);
                    printf("Digit the product price: ");
                    scanf(" %f", &p1[tam].price);
                    tam++;
                } else {
                    printf("***Realloqing: %d***\n", tam * sizeof(*p1));
                    p1 = (Product*)realloc(p1, (tam) * sizeof(Product));
                    for (i = tam; i > 0; i--) {
                        p1[i].cod = p1[i-1].cod;
                        p1[i].price = p1[i-1].price;
                    }
                    printf("Digit the product code: ");
                    scanf(" %d", &p1[0].cod);
                    printf("Digit the product price: ");
                    scanf(" %f", &p1[0].price);
                    tam++;
                }
            break;
            case 2:
                for (i = 0; i < tam; i++) {
                    printf("Product code: %d\nProduct price: %f\n", p1[i].cod, p1[i].price);
                }
            break;
            case 3:
                control = 0;
            break;
        }

    } while (control);

    for (int i = 0; i < tam; i++){
        fwrite(&p1[i], sizeof(Product), 1, fp);
    }

    fclose(fp);

    free(p1);

    return 0;
}
#包括
#包括
类型定义结构{
国际化学需氧量;
浮动价格;
}产品;
int main(){
文件*fp;
fp=fopen(“products.txt”、“r+”);
如果(fp==NULL)
fopen(“products.txt”、“w+”);
int控制=1;
智力选择;
int-tam=0;
int i;
产品*p1;
p1=malloc(产品尺寸);
while(fread(&p1[0],sizeof(Product),1,fp)!=NULL){
tam++;
}
如果(tam>1){
倒带(fp);
p1=malloc((tam)*sizeof(*p1));
for(int i=0;i”);
scanf(“%d”,选择(&C);
开关(选择){
案例1:
如果(tam==0){
//p1=malloc(产品尺寸);
printf(“产品代码的数字:”);
scanf(“%d”,&p1[tam].cod);
printf(“产品价格的数字:”);
scanf(“%f”、&p1[tam].价格);
tam++;
}否则{
printf(“***Realloqing:%d***\n”,tam*sizeof(*p1));
p1=(产品*)realloc(p1,(tam)*sizeof(产品));
对于(i=tam;i>0;i--){
p1[i].cod=p1[i-1].cod;
p1[i]。价格=p1[i-1]。价格;
}
printf(“产品代码的数字:”);
scanf(“%d”,&p1[0].cod);
printf(“产品价格的数字:”);
scanf(“%f”,&p1[0]。价格);
tam++;
}
打破
案例2:
对于(i=0;i
这是:

p1 = (Product*)realloc(p1, (tam) * sizeof(Product));
违反了Realloc的第一条规则,即不能将Realloc的结果直接分配给作为其第一个参数传递的同一个变量。当您这样做时,如果失败,您就丢失(泄漏)了旧指针

其次,不检查各种函数的返回值,例如
malloc()
realloc()
、和
scanf()
。这也是大罪

如果修复了所有仍然导致程序损坏的问题,请使用valgrind。

问题在于:

    printf("***Realloqing: %d***\n", tam * sizeof(*p1));
    p1 = (Product*)realloc(p1, tam * sizeof(Product));
tam
为1时,则您需要realloc
tam*sizeof(Product)
,但您需要realloc
(tam+1)*sizeof(Product)
,因为现在您需要2产品的空间

因此,这解决了问题:

    printf("***Realloqing: %d***\n", (tam + 1) * sizeof(*p1));
    p1 = (Product*)realloc(p1, (tam + 1) * sizeof(Product));

有两件事:首先,您不应该将指针分配回传递给
realloc
,如果
realloc
失败并返回空指针,您将丢失原始指针并导致内存泄漏。然后你应该阅读。至于你的问题,你写的东西似乎超出了你分配的内存范围。您可能希望使用诸如之类的工具来帮助您发现此类问题。
fopen(“products.txt”、“w+”->
fp=fopen(“products.txt”、“w+”)
@MichaelWalz感谢我没有看到它
tam
是int,而
sizeof
产生
size\u t
(一种无符号类型)。在做像
int*size\t
这样的事情时要小心,你确定“Realloc的第一条规则”吗?声明:如果内存对象的新大小需要移动该对象,则会释放该对象上一次实例化的空间。@KeineLust:是的,我确定。请注意,我说的是“如果失败”。你认为它成功了。我在哪里可以读到更多关于第一条规则等戒律的内容?在这里,它仍然失败。顺便说一句,
realloc
malloc
等。在玩具程序中返回
NULL
是不太可能发生的。@anaeath,哦,我刚刚发布了一个答案,但是的,这就是问题所在。