-1

我想从 b->array 中删除元素,如下代码所示:removeItem函数我试图从 b->array = {11.11,12.12,13.13} 中删除 12.12 但它会导致分段错误而不是打印 {11.11, 13.13}。任何人都可以帮助摆脱它吗?

typedef struct
{
  float val;
}data;

typedef struct
{
  data **array;
  int size;
}bag;
int main(int argc,char* argv[])
{

    bag *str = createBag(); 
    #ifdef DEBUG
    printf("Inital values: %p %d\n",str->array,str->size);
    #endif
    data *iptr = createData(10.10);
    data *iptr1 = createData(11.11);
    data *iptr2 = createData(12.12);
    data *iptr3 = createData(13.13);
    data *iptr4 = createData(14.14);
    #ifdef DEBUG
    printf("%f\n",iptr->val);
    #endif
    addData(str,iptr);
    addData(str,iptr1);
    addData(str,iptr2);
    addData(str,iptr3);
    addData(str,iptr4);
    printBag(str);
    data *ptr = getData(str,4);
    printf("Data item 4 is:%f\n",ptr->val);
    int b = getBagSize(str);
    printf("Size of bag: %d\n",b);
    removeBack(str);
    printBag(str);
    removeFront(str);
    printBag(str);
    //cleanBag(str);
    int s = searchBag(str,10.10);
    printf("%d\n",s);
    removeItem(str,12.12);
    printBag(str);
  return 0;
}


bag* createBag()
{
    bag *str = (bag*)malloc(sizeof(bag));
    str->array = NULL;
    str->size = 0;
    return str;
}

data* createData(float v)
{
    data *iptr = (data*)malloc(sizeof(data));
    iptr->val = v;
    return iptr;
}

void addData(bag* b, data* d)
{
    b->size++;

    data** array1 = (data**)malloc(sizeof(data*)* b->size);



    if(b->array!= NULL)
    {
        int i;
        for(i = 0; i<b->size;i++)
        {
            array1[i] = b->array[i];
        }
    }

    free(b->array);
    array1[b->size-1] = d;

    b->array = array1;

}

void printBag(bag *b)
{
    int i;
    for(i=0; i<b->size;i++)
    {
        printf("%f\n",b->array[i]->val);
    }
}

data* getData(bag *b, int pos)
{

    if(pos>5)
    {
        printf("change array position\n");
    }   
    return b->array[pos];


}

int getBagSize(bag *b)
{
    return b->size;

}

void removeBack(bag *b)
{
    b->size--;
    free(b->array[b->size]);

    data **array2 = (data**)malloc(sizeof(data*)* b->size);

    if(b->array!= NULL)
    {
        int i;
        for(i = 0; i<b->size;i++)
        {
            array2[i] = b->array[i];
            #ifdef DEBUG
            printf("%f\n",array2[i]->val);
            #endif
        }

    free(b->array);
    b->array = array2;
    }
}

void removeFront(bag *b)
{
    b->size--;
    free(b->array[0]);

    data **array2 = (data**)malloc(sizeof(data*)* b->size);

    if(b->array!= NULL)
    {
        int i;
        for(i = 0; i<b->size;i++)
        {
            array2[i] = b->array[i+1];
            #ifdef DEBUG
            printf("%f\n",array2[i]->val);
            #endif
        }

    free(b->array);
    b->array = array2;
    }

}
/*void cleanBag(bag *b)
{
    int i;
    for(i=0;i<b->size;i++)  
    {
        free(b->array[i]);
    }
    free(b->array);
    free(b);        
}*/

int searchBag(bag *b,float v)
{
    int i;
    for(i=0;i<b->size;i++)
    {

        if(b->array[i]->val==v)
        {
            return (i+1);
        }
    }
    return -1;
}

void removeItem(bag *b, float v)
{
    int flag = 0,i = 0;

    flag = searchBag(b,v); 
    if(flag != -1) 
    { 
        data **array2 = (data**)malloc(sizeof(data*)*(b->size-1));

        for(i = 0; i < (b->size); i++) 
        { 
             if(i == (flag-1))
            { 
                i = i + 1;
                continue; 
            } 

            array2[i] = b->array[i]; 
        } 
        free(b->array); 
        b->size--; 
        b->array = array2; 
    } 
    else 
    {
        printf("Element is not found\n");
    }
}
4

1 回答 1

0

您的代码中有两个错误。

  1. 如果在包中找不到浮点值,则searchBag返回 0。但是,函数removeItem测试if(flag != -1). 它应该测试if(flag != 0)

  2. 段的原因。您遇到的故障还在于removeItem函数。请注意为array2分配的内存仅用于 b->size-1 元素。此数组的有效数组索引在 0 ... b->size-2范围内。现在,查看 for 循环,您会注意到索引变量 i 将从 0 运行到b->size-1。恰好在最后一次迭代中,i 将变为 b->size-1,因此代码尝试写入array2[b->size-1]超出 array2 分配内存的位置。


removeItem函数 的可能修复可能如下所示:

void removeItem(bag *b, float v)
{
    int flag = 0;
    int oldArrayIndex = 0;
    int newArrayIndex = 0;

    flag = searchBag(b,v); 
    if(flag != 0) 
    { 
        data **array2 = (data**) malloc(sizeof(data*)*(b->size-1));

        for(oldArrayIndex = 0; oldArrayIndex < (b->size); oldArrayIndex++) 
        { 
            if(oldArrayIndex != (flag-1))
            { 
                array2[newArrayIndex] = b->array[oldArrayIndex]; 
                newArrayIndex++;
            } 
        } 
        free(b->array); 
        b->size--; 
        b->array = array2; 
    } 
    else 
    {
        printf("Element is not found\n");
    }
}
于 2013-10-29T22:43:07.487 回答