c - 我该如何解决这个分配问题(核心转储)?

标签 c

我编写了一个程序来接收两个多项式并计算它们的和乘法。

程序以这种形式得到一个多项式

"2   4   -5   1   0   6   6   4   -8   0   7   3"

并将其转化为多项式形式:“8x^4+7x^3-5x-8”

我想我对多项式求和函数有问题,因为它确实显示了乘法结果。

这是我得到的错误:

*** Error in `./vpl_execution': realloc(): invalid next size: 0x000000000070c210
 ***                                                                            
/home/p18206/.vpl_launcher.sh: line 9: 25054 Aborted                 (core dumpe
d) ./vpl_execution   

还有另一个错误:

ome/p13634/.vpl_launcher.sh: line 9: 25304 Segmentation fault      (core dumpe
d) ./vpl_execution                                                              

我真的尝试了一切, 我知道这是一个分配问题,但我就是不明白为什么。

所以在下面的代码中,请检查函数“print polySum”。 也有可能是函数“sum same power poly”或者“print polynom”有问题

    #define _CRT_SECURE_NO_WARNINGS
    #include <stdio.h>
    #include <stdlib.h>
    #include <string.h>

    typedef struct monom {
        int coefficient;
        int power;
    }Monom;

    //defining bool data type
    typedef int bool;
    #define TRUE 1
    #define FALSE 0

    #define MEMORY_ERROR_EXIT -1

    void polyMerge(Monom* arr1, unsigned int size1, Monom* arr2, unsigned int size2, Monom* res);
    void polySort(Monom* polynom, unsigned int size);
    void removeElement(Monom* polynomArr, unsigned int size);
    Monom* sumSamePowerPoly(Monom* polynomArr, unsigned int* size);
    Monom* getPolynom(unsigned int* size);
    void printPolynom(Monom* polynom, unsigned int size);
    void printPolySum(Monom* polynom1, unsigned int size1, Monom* polynom2, unsigned int size2);
    void printPolyMul(Monom* polynom1, unsigned int size1, Monom* polynom2, unsigned int size2);
    void checkMemoryAllocation(void *ptr);

    void main()
    {
        Monom *polynom1, *polynom2;             // The input polynoms
        unsigned int polynom1Size, polynom2Size; // The size of each polynom

        printf("Please enter the first polynom:\n");
        polynom1 = getPolynom(&polynom1Size);   // get polynom 1

        printf("Please enter the second polynom:\n");
        polynom2 = getPolynom(&polynom2Size);   // get polynom 2

        printf("The multiplication of the polynoms is:\n"); // print the multiplication
        printPolyMul(polynom1, polynom1Size, polynom2, polynom2Size);
        printf("\n");

        printf("The sum of the polynoms is:\n"); // print the sum
        printPolySum(polynom1, polynom1Size, polynom2, polynom2Size);
        printf("\n");

        free(polynom1); // releasing all memory allocations
        free(polynom2);
    }

    Monom* getPolynom(unsigned int* size) {
        /*This function recieve data from user*/

        unsigned int phySize = 1, logSize = 0;
        int currCofficient, currPower;
        bool lContinue = TRUE; // a flag that keeps that signal if we should keep recieving input
        Monom* polyArr;
        polyArr = (Monom*)malloc(sizeof(Monom)*phySize);
        checkMemoryAllocation(polyArr);

        while (lContinue) { //while the user didn't press enter we keep on recieving input
            scanf("%d%d", &currCofficient, &currPower);
            if (currCofficient != 0) { //if the current cofficient is 0 we do nothing. Else we insert the input to the array
                                       //if the logic size equal to the physical size we double the phySize and reallocate array with the new size
                if (logSize == phySize) {
                    phySize *= 2;
                    polyArr = (Monom*)realloc(polyArr, sizeof(Monom)*phySize);
                    checkMemoryAllocation(polyArr);;
                }
                polyArr[logSize].coefficient = currCofficient; //we locate the input on the current position (logical size)
                polyArr[logSize].power = currPower;
                logSize++; //we increment logical size of the array
            }

            if (getchar() == '\n') // the user pressed enter - the flag is "turned off", and we stop receiving input
                lContinue = FALSE;
        }

        *size = logSize; //size recieve the value "log size" which is the actual size of the array
        polySort(polyArr, *size); //we sort the array based on power sizes
        polyArr = sumSamePowerPoly(polyArr, size); //we unite Monoms that has the same power
        return polyArr;
    }


    void polyMerge(Monom* arr1, unsigned int size1, Monom* arr2, unsigned int size2, Monom* res) {
        /*This function merges two Monom arrays into one monom array sorted by powers from the biggest power to the smallest one*/
        unsigned int i = 0, j = 0, k = 0;
        while (i < size1 && j < size2) {
            if (arr1[i].power > arr2[j].power)
                res[k++] = arr1[i++];
            else
                res[k++] = arr2[j++];
        }

        while (i < size1) //While i<size1 keep copying values from array 1 to result array
            res[k++] = arr1[i++];
        while (j < size2) //While j<size2 keep copying values from array 2 to result array
            res[k++] = arr2[j++];
    }
    void polySort(Monom* polynom, unsigned int size) {
        /*This function sort a Monom array from the biggest power to the smalles one*/
        Monom* temp;
        unsigned int i;
        if (size == 1)
            return;
        else {
            polySort(polynom, size / 2);
            polySort(polynom + size / 2, size - size / 2);
            temp = (Monom*)malloc(sizeof(Monom)*size); //We temporary allocate an array that will keep the result of the merge
            checkMemoryAllocation(temp);
            polyMerge(polynom, size / 2, polynom + size / 2, size - size / 2, temp);

            for (i = 0; i < size; i++) //We copy the temporary array into our data array
                polynom[i] = temp[i];
            free(temp); //We delete the allocated memory for the temporary array
        }
    }


    Monom* sumSamePowerPoly(Monom* polynomArr, unsigned int* size) {
        /*This function sum polynoms from the same degree to one polynom*/
        unsigned int i;
        for (i = 0; i < *size - 1; i++) { //We check for each Monom in the array if there are other monoms with the same power
            while (polynomArr[i].power == polynomArr[i + 1].power) { //while power of a monom is eqaul to the power of other monoms
                polynomArr[i].coefficient += polynomArr[i + 1].coefficient; //we add the next monom to the first one
                removeElement(polynomArr + i + 1, *size - i); //and remove the monom we just united into another cell
                *size -= 1;
            }
        }
        polynomArr = (Monom*)realloc(polynomArr, sizeof(Monom)*(*size));
        return polynomArr;
    }

    void removeElement(Monom* polynomArr, unsigned int size) {
        /*This function removes an element from array*/
        unsigned int i;
        for (i = 0; i < size; i++) { //We copy each cell into the prior one
            polynomArr[i] = polynomArr[i + 1];
        }
    }

    void printPolynom(Monom* polynom, unsigned int size) {
        /*This function prints polynom*/
        unsigned int i;
        for (i = 0; i < size; i++) {
            if (polynom[i].power > 1) //if the power is bigger than one that print this form: coffx^power
                printf("%dx^%d", polynom[i].coefficient, polynom[i].power);
            else if (polynom[i].power == 1) //else if the power is one than print this form: coffx
                printf("%dx", polynom[i].coefficient);
            else //else print this form: coff
                printf("%d", polynom[i].coefficient);
            if (i < size - 1 && polynom[i + 1].coefficient > 0) //if there is another element after the current element and its
                                                                //cofficient is larger than 0 - print "+"
                printf("+");
        }
    }
    void printPolySum(Monom* polynom1, unsigned int size1, Monom* polynom2, unsigned int size2) {
        /*This function print the sum of two polynoms*/
        unsigned int i, j;
        unsigned int size;
        size = size1 + size2; //We set the size of sum result to be size of both of the polynoms

    Monom* sumRes; //We create a sum result array
    sumRes = (Monom*)malloc(sizeof(Monom)*size);
    checkMemoryAllocation(sumRes);
    //We copy each element from both of the polynoms array into the result array
    for (i = 0; i < size1; i++)
        sumRes[i] = polynom1[i];
    for (i = size1, j = 0; i < size && j < size2; j++, i++) {
        sumRes[i] = polynom2[j];
    }
    polySort(sumRes, size); //We sort all of the elements by power size
    //We unite all of the cells who has the same power. This action actually sums both of the polynoms to one poly sum.
    sumRes = sumSamePowerPoly(sumRes, &size);
    printPolynom(sumRes, size); //We print sum reault
    free(sumRes); //We free the sum result array after printing it
}

void printPolyMul(Monom* polynom1, unsigned int size1, Monom* polynom2, unsigned int size2) {
    /*This function prints the multiplication of two polynoms*/
    unsigned int i, j, k, size;
    i = 0;
    Monom* mulRes;
    size = size1 * size2; //We set the size of sum result to be the multiplication of both of the polynoms size
    mulRes = (Monom*)malloc(sizeof(Monom)*size); //We create a multiplication result array in which we will store the result of multiplying polynoms
    checkMemoryAllocation(mulRes);
    Monom temp; //We creat a temporary data type monom in which we will save the calculation of each multiplication
                //We multiply the polynoms and keep the multiplication result in the mulRes array
    for (j = 0; j < size1; j++) {
        for (k = 0; k < size2; k++) {
            temp.coefficient = polynom1[j].coefficient*polynom2[k].coefficient;
            temp.power = polynom1[j].power + polynom2[k].power;
            mulRes[i++] = temp;
        }
    }
    polySort(mulRes, size); //We sort all of the elements by power size
    mulRes = sumSamePowerPoly(mulRes, &size); //We unite all of the cells who has the same power
    printPolynom(mulRes, size); //We print the multiplication result
    free(mulRes);  //We free the multiply result array after printing it
}

void checkMemoryAllocation(void *ptr)
/*This function check if the dynmic allocation we did has succseeded */
{
    if (ptr == NULL)
    {
        printf("Memory allocation error\n");
        exit(MEMORY_ERROR_EXIT);
    }
}

这是预期的结果: 多项式的乘法是: 64x^8+112x^7+49x^6-80x^5-198x^4-112x^3+25x^2+80x+64 多项式之和为: 16x^4+14x^3-10x-16

非常感谢您抽出宝贵时间!

最佳答案

在函数 GetPolynom 中我发现了这个:

   if (logSize == phySize) {
        phySize *= 2;
        polyArr = (Monom*)realloc(polyArr, sizeof(Monom)*phySize);
        checkMemoryAllocation(polyArr);;
   }

这意味着您正在重新分配以指数形式增长的大小 sizeof(Monom) * 2^(n-1) n 是“while”构造中当前循环的数量。

我认为你应该改变

     phySize *= 2;

对于

     phySize += 1;

希望这对您有所帮助。

关于c - 我该如何解决这个分配问题(核心转储)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57358014/

相关文章:

c - 二进制搜索以获取第一个整数的位置 >= 搜索到的整数

c++ - Cudd:提取变量排序

c - C 中的大位数组

计算 "based"数据校验和。 (SHA1/2 等)

c - 如何在 C 中的字符串中查找字符串?

c - 使用 makefile 移动现有文件

c - 从文件读取数据时无限循环

c - 在 C 中创建集合的良好平均速度/内存效率方法? :

c - 为什么来自 "Learn C the hard way"的示例在 valgrind 中显示错误?

c - 在方法中传递数组并获取它的大小