Problem with "Graduation" exercise.

I'm having trouble with the "Graduation" exercise in the Beginner Exercises thread. I've gotten almost everything working, except that sometimes, randomly, at the end of a cycle, I'll get a segmentation fault. I think it may have something to do with how I'm deleting random bunnies from my list during food shortages. Here is my main.cpp file:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
/**
* CPlusPlus.com Beginner Exercises - Graduation ( http://cplusplus.com/forum/articles/12974/ )
* Author - packetpirate
* Last Update - 10/17/2011
**/

#include <iostream>
using std::cout;
using std::cin;
using std::endl;
#include <ctime>
#include "includes/Bunny.h"
#include "includes/List.h"
using LList::List;
#include "includes/Random.h"
using RandomF::Random;

void stop(const char * message);
void mainLoop();

int main(int argc, char ** argv) {
    srand((unsigned)time(0));

    cout << "Welcome to Bunny Life v1.0" << endl;

    mainLoop();

    return 0;
}

void stop(const char * message) {
    cin.sync();
    cout << message;
    cin.get();
}

void mainLoop() {
    List<Bunny*> * bunnies = new List<Bunny*>();
    cout << "Five bunnies are being born!" << endl;
    for(int i = 0;i < 5;i++) {
        bunnies->add(new Bunny());
    }

    cout << endl;

    for(int i = 0;i < 5;i++) {
        cout << "Bunny " << bunnies->get(i)->getName() << " was born" << ((bunnies->get(i)->isVampire())?" a vampire.":".") << endl;
        cout << "Gender: " << ((bunnies->get(i)->getGender() == 0)?"Male":"Female") << endl;
        cout << "Color: " << bunnies->get(i)->getColorText() << endl;
        cout << endl;
    }

    int numOfBunnies = bunnies->length();
    int years = 0;

    while(numOfBunnies > 0) {
        // BEGIN MAIN PROCESS

        // If there is at least one female and one male, a bunny will be born.
        for(int i = 0;i < numOfBunnies;i++) {
            if((bunnies->get(i)->getGender() == MALE)&&(bunnies->get(i)->getAge() >= 2)&&(!(bunnies->get(i)->isVampire()))) {
                for(int j = 0;i < numOfBunnies;i++) {
                    if((bunnies->get(j)->getGender() == FEMALE)&&(bunnies->get(j)->getAge() >= 2)&&(!(bunnies->get(j)->isVampire()))) {
                        Bunny * newBunny = new Bunny((bunnies->get(j)->getColor()));
                        bunnies->add(newBunny);
                        cout << endl;
                        cout << "Bunny " << newBunny->getName() << " was born" << ((newBunny->isVampire())?" a vampire.":".") << endl;
                        cout << "Gender: " << ((newBunny->getGender() == 0)?"Male":"Female") << endl;
                        cout << "Color: " << newBunny->getColorText() << endl;
                        cout << endl;
                    }
                }
            }
        }

        // END MAIN PROCESS

        // If there are any vampires, they will now convert a random non-vampire Bunny.

        // Bunnies will now age.
        for(int i = 0;i < bunnies->length();i++) {
            bunnies->get(i)->mature();
            if(!(bunnies->get(i)->isVampire())) {
                if(bunnies->get(i)->getAge() > 10) {
                    cout << "Bunny " << bunnies->get(i)->getName() << " has died!" << endl;
                    bunnies->remove(i);
                }
            } else {
                if(bunnies->get(i)->getAge() > 50) {
                    cout << "Vampire Bunny " << bunnies->get(i)->getName() << " has died!" << endl;
                    bunnies->remove(i);
                }
            }
        }

        // Update Bunny count.
        numOfBunnies = bunnies->length();
        cout << "There are " << numOfBunnies << " bunnies left." << endl;

        // If there is a population overflow, half of all bunnies die.
        if(numOfBunnies >= 1000) {
            cout << "There has been a food shortage. Half of the bunnies die!" << endl;
            for(int i = 0;i < (numOfBunnies / 2);i++) {
                int die = Random(0,(numOfBunnies - 1));
                bunnies->remove(die);
                numOfBunnies = bunnies->length();
            }
        }

        // Update year count.
        cout << "End of year " << years << "." << endl;
        stop("Press any key to continue...");
        years++;
    }

    cout << "All the bunnies have died. Game over." << endl;
}


My program is pretty large, so if you need me to post the Bunny class or my Linked List class, let me know. Also, the Random() function returns numbers in an inclusive range. Let me know if I left out any information. I would post sample output, but there are over 1,000 lines by the time it runs into this problem.

I'm terrible with segmentation faults... =/
Someone must have an answer for me...

Also, new problem. Yesterday, it was working fine, but today, I loaded the program and no new bunnies were being born, even though I was getting an even amount of males and females. I have no idea what's wrong and why it's doing this.

EDIT: Fixed the problem where bunnies weren't being born. For some reason, my header files weren't set to link with the project. Now, my problem is that segmentation fault. It only happens in the phase where bunnies die. So the problem must lie somewhere in this section:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
        // Bunnies will now age.
        for(int i = 0;i < bunnies->length();i++) {
            bunnies->get(i)->mature();
            if(!(bunnies->get(i)->isVampire())) {
                if(bunnies->get(i)->getAge() > 10) {
                    cout << "Bunny " << bunnies->get(i)->getName() << " has died!" << endl;
                    bunnies->remove(i);
                }
            } else {
                if(bunnies->get(i)->getAge() > 50) {
                    cout << "Vampire Bunny " << bunnies->get(i)->getName() << " has died!" << endl;
                    bunnies->remove(i);
                }
            }
        }


But I don't see what could be causing the problem. I've checked the constructors and I'm not forgetting to assign anything... and even if I had, the segmentation fault would have come when the Bunny object was first created. So why is a segmentation fault happening when I try to kill off the Bunny objects? And why is it only happening sometimes? Sometimes, it works just fine, and will go through several cycles killing off bunnies without any problems, but then it will seg fault on a random cycle.

Does anyone have any insight into my problem?
Last edited on
Well I am not sure it's much help but segfault have to do with (possible problem cause):

uninitialized pointer use

boundary overflow (arrays maybe?)

dereferencing NULL pointer

That's that came up.

As you can figure out I haven't read your code. Anyway if it can be of any help...
Okay, I THOUGHT I had solved the problem, but now I'm occasionally getting that problem again where no bunnies are born. It's random, even when the distribution of males and females in the first 5 bunnies is even.

Can ANYONE see what's causing either problem?
Topic archived. No new replies allowed.