哈希表seg fault

时间:2015-04-24 07:56:16

标签: c++

所以我真的不确定导致seg错误的是什么,但我觉得它与hashTables有关,因为调试器在它所涉及的这一行显示了seg错误。

以下是导致seg错误的代码

//Constructor for hashtable
HashTable::HashTable()
{
    for(int i = 0; i < 10; i++)
    {
        hashTable[i] = new Movie;
        hashTable[i]->title = "empty";
        hashTable[i]->year = 0;
        hashTable[i]->next = NULL;
    }
}

//destructor for hashtable
HashTable::~HashTable()
{

}

// this will take a string and convert the letters to hash numbers then add them all together and divide by the hash table size to get a index
int HashTable::initHash(std::string in_title)
{
    int hashT = 0;
    int index = 0;

    for(int i = 0; i < in_title.length(); i++)
    {
        hashT = hashT + (int)in_title[i];
        std::cout << "hash = " << hashT << std::endl;
    }

    index = hashT % 10;
    std::cout << "index = " << index << std::endl;

    return index;
}

//This is where we will be inserting a new Movie into the hashtable, 
//it will first use initHash to find the number of where it should go in the hash and then from there add it to the hashtable
void HashTable::insertMovie(std::string in_title, int year)
{
    int index = initHash(in_title);
    std::cout << "index = " << index << std::endl;

    if (hashTable[index]->title == "empty") // *** seg faults right here ***
    {
        hashTable[index]->title = in_title;
        hashTable[index]->year = year;
    }

    else
    {
        Movie* Ptr = hashTable[index];
        Movie* n = new Movie;
        n->title = in_title;
        n->year = year;
        n->next = NULL;
        while(Ptr->next != NULL)
        {
            Ptr = Ptr->next;
        }
        Ptr->next = n;
    }
}

在我的每个包含hashTables [index]的函数中它都有错误但我不确定为什么,索引会返回一个应该有效的数字。有谁知道为什么会这样?

编辑:好的,这是我的头文件

中的两个类
struct Movie{
    std::string title;
    int year;
    Movie *next;

    Movie(){};

    Movie(std::string in_title, int in_year)
    {
        title = in_title;
        year = in_year;
    }

};

class HashTable
{
    public:
        HashTable();
        ~HashTable();
        void insertMovie(std::string in_title, int year);
        int initHash(std::string in_title);
        int NumberofItemsInIndex(int index);
        Movie* findMovie(std::string in_title/*, int *index*/);
        void deleteMovie(std::string in_title);
        void printInventory();
        void PrintItemsInIndex(int index);
    protected:
    private:
        Movie **hashTable;
};

编辑2:这是main()函数

int main(int argc, char * argv[])
{
    // Declarations
    int input; // Declaring an input for the menu
    bool quit = false; // Bool for the menu
    //string title; // input value for certain actions
    //int year; // input value for certain actions

    HashTable *ht;
    //int index;

    //readFileIntoHash(ht, argv[1]);



    while(quit != true)
    {
        displayMenu(); // Displays the main menu
        cin >> input;

        //clear out cin
        cin.clear();
        cin.ignore(10000, '\n');

        switch (input)
        {

        // Insert a movie
        case 1:
            {
                string in_title;
                int year;
                cout << "Enter Title:" << endl;
                cin >> in_title;
                cout << "Enter Year:" << endl;
                cin >> year;
                ht -> insertMovie(in_title, year);
                break;
            }

        // Delete a movie
        case 2:
            {
                string in_title2;
                cout << "Enter Title:" << endl;
                cin >> in_title2;
                ht -> deleteMovie(in_title2);
                break;
            }

        // Find a movie
        case 3:
            {
                string in_title3;
                cout << "Enter Title:" << endl;
                cin >> in_title3;
                ht -> findMovie(in_title3);
                break;
            }

        // Print table contents
        case 4:
            ht -> printInventory();
            break;

        case 5:
            cout << "Goodbye!" << endl;
            quit = true;
            break;

            // invalid input
        default:
            cout << "Invalid Input" << endl;
            cin.clear();
            cin.ignore(10000,'\n');
            break;
        }
    }
    return 0;
}

void displayMenu()
{
    cout << "======Main Menu=====" << endl;
    cout << "1. Insert movie" << endl;
    cout << "2. Delete movie" << endl;
    cout << "3. Find movie" << endl;
    cout << "4. Print table contents" << endl;
    cout << "5. Quit" << endl;
    return;
}

为了清楚起见,我添加了displayMenu()。

3 个答案:

答案 0 :(得分:2)

修改类定义:

class HashTable
{
    public:
        HashTable();
        ~HashTable();
        void insertMovie(std::string in_title, int year);
        int initHash(std::string in_title);
        int NumberofItemsInIndex(int index);
        Movie* findMovie(std::string in_title/*, int *index*/);
        void deleteMovie(std::string in_title);
        void printInventory();
        void PrintItemsInIndex(int index);
    protected:
    private:
        Movie *hashTable[10]; /*<<-- since your size is fixed use an array*/
};

另外..因为你在构造函数中分配了Movies,所以记得在析构函数中释放它们:

//destructor for hashtable
HashTable::~HashTable()
{
    for(int i = 0; i < 10; i++)
    {
        delete hashTable[i];
    }
}

替代方案,使用动态分配的内存(具有相同的类定义)

HashTable::HashTable()
{
    hashTable = new (Movie*) [10];
    for(int i = 0; i < 10; i++)
    {
        hashTable[i] = new Movie;
        hashTable[i]->title = "empty";
        hashTable[i]->year = 0;
        hashTable[i]->next = NULL;
    }
}

HashTable::~HashTable()
{
    for(int i = 0; i < 10; i++)
    {
        delete hashTable[i];
    }
    delete[] hashTable;
}

其他修正:

修改主要功能:

int main(int argc, char * argv[])
{
    // Declarations
    int input; // Declaring an input for the menu
    bool quit = false; // Bool for the menu
    //string title; // input value for certain actions
    //int year; // input value for certain actions

    HashTable ht; // <<==== local variable, not a pointer!

...然后将ht->xxxx(...)替换为ht.xxxx(...)其他地方。

答案 1 :(得分:0)

hashTable[i] = new Movie;你为电影分配内存

Movie **hashTable;的内存未被分配

尝试将hashTable = new Movie *[100];添加到构造函数

答案 2 :(得分:0)

这个构造函数可能是:

HashTable::HashTable()
{
    hashTable = new (Movie*) [10]; // Allocate memory on the heap for the array
    for(int i = 0; i < 10; i++)
    {
        hashTable[i] = new Movie;
        hashTable[i]->title = "empty";
        hashTable[i]->year = 0;
        hashTable[i]->next = NULL;
    }
}

但是,实际上不需要在hashmap中有一个Movie指针数组,你只需要一个Movie个对象数组。实际上,你想要的一个链表,所以我的坏。另外,我不会在任何地方写10,而是使用常量,以便稍后更改大小。

当你让它工作时,你应该写一个析构函数来避免内存泄漏。提示:通过拨打new(以及delete new[])来呼叫delete[]的每个电话。