Search code examples
c++arrayssegmentation-faultmallocrealloc

Segfault with String array C++


Had this program in C and was trying to convert some to C++ as I learn the language. Basically char arrays to strings and some of the input/output. Only issue is I get a segfault when attempting to put the input string into the string array (test2 prints. test3 does not).

Any ideas? Any bad coding habits I should be aware of as I learn c++?

int main() {
int nstr=0, nchar=0, nint=0, nfloat=0;
string input;
int i, z=0;
float inputFloat;

string *strList = (string*)malloc(sizeof(string) * nstr);
char *charList = (char*)malloc(sizeof(char) * nchar);
int *intList = (int*)malloc(sizeof(int) * nint);
float *floatList = (float*)malloc(sizeof(float) * nfloat);

while (z != -42) {
    cout << "Input:  ";
    cin >> input;
    cin.ignore();

    inputFloat = strtof(input.c_str(), NULL);

    if (inputFloat) {
        if (fmod(inputFloat, 1.0)) {
            nfloat++;
            floatList = (float*)realloc(floatList, sizeof(float) * nfloat);
            floatList[nfloat-1] = inputFloat;
        }
        else {
            nint++;
            intList = (int*)realloc(intList, sizeof(int) * nint);
            intList[nint-1] = (int)inputFloat;
        }
    }
    else {
        if (input.length() == 1) {
            nchar++;
            charList = (char*)realloc(charList, sizeof(char) * nchar);
            if (input.at(0) == 10)
                input = " ";
            charList[nchar-1] = input.at(0);
        }
        else {
            nstr++;
            cout << "test1" << endl;
            strList = (string*)realloc(strList, sizeof(string) * nstr);
            cout << "test2" << endl;
            strList[nstr-1] = input;
            cout << "test3" << endl;
        }
    }

    cout << "Integers: ";
    for (i=0; i<nint; i++)
        cout << intList[i] << " ";

    cout << endl << "  Floats: ";
    for (i=0; i<nfloat; i++)
        cout << floatList[i] << " ";

    cout << endl << "   Chars: ";
    for (i=0; i<nchar; i++)
        cout << charList[i] << " ";

    cout << endl << " Strings: ";
    for (i=0; i<nstr; i++)
        cout << strList[i] << " ";
    cout << endl << endl;
}
}

Solution

  • As a rule you don't use malloc,calloc,realloc etc. in c++ at all, even though you can. It less meaningful for simple items like: int, char etc. but when using on objects (like std::string) it cause this kind of problems:

    When this line runs:

    string *strList = (string*)malloc(sizeof(string) * nstr);

    You allocate storage to array of strings, but you didn't called any constructor, therefor all the storage you've allocated is still useless.

    In c++ you must use new like this:

    string *strList = new string[nstr];

    it is shorter, easier and call the constructor of each allocated object.

    In the end you dealocate it with delete [] like this:

    delete [] strList;

    Even better is to use:

    vector<string> strList;

    and add elements by using:

    strList.push_back("something"); or strList.push_back(some_string);

    vectors are take care for the memory allocation and free, and are freed automatically as regular object at end of life, so it won't needed to be deleted at all.