First Tree class...could use some help

Pages: 12
Last piece of the puzzle: Where is it still reading in spaces, and how do I get rid of them?
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
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
#include <iostream>
#include <string>
#include <iomanip>
#include <fstream>

using namespace std;

// File descriptors
ifstream infile;
ofstream outfile;

typedef string tType;           // Variable to hold each word

class tNode                     // Node class within the tree class
{
public:
        // Member Variables
        tType value;            // Holds each word
        tNode* left;            // Points to left tree node
        tNode* right;           // Points to right tree node
        int counter;            // Counts instance of each word

        // Construct / Destruct
        tNode(tType v);
        ~tNode(void);
};

class tTree                     // Actual tree class
{
private:
        // Member Variables
        tNode* root;            // Tree root pointer

        // Private Member Functions
        void destroy(tNode* current);                   // Apparently, this prevents memory leaks
        void rInsert(tNode** current, tNode* newNode);  // Inserts words into the tree
        void rPrint(tNode* current);                    // Prints out the tree

public:
        // Construct / Destruct
        tTree(void);
        ~tTree(void);

        // Public Member Functions
        // Modifiers
        void clear(void);           // Clears the tree
        void insert(tType newValue);// Inserts into the tree

        // Accessors
        void print(void);           // Prints the tree
};

// Function prototypes
int open_output();
int open_input();
void print_header();
tType clean_up(tType x);

float totalCounter = 0;                 // Counts total number of words in input file
string alphabet = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";

//Main program
int main(void)
{
        open_output();
        open_input();
        print_header();

        tTree myTree;                   // Create a tree
        string con_word;                // Create a variable to hold each word

        // Print out header
        cout << setw(30) << "WORD" << setw(10) <<  "ABSOLUTE" << setw(10) << "RELATIVE" << endl << endl;

        infile >> con_word;             // Get first word of input file

        while (infile)                  // While still in input file
        {
            myTree.insert(clean_up(con_word));// Add word to the list
            totalCounter++;             // Add to total counter
            infile >> con_word;         // Get next word
        }

        myTree.print();                 // Print out the tree

        cout << fixed;
        cout << endl << "Total number of words: " << setprecision(0) << totalCounter << endl;
    return 0;
}

//***************************************************************
// tNode Functions
// Construct / Destruct
tNode::tNode(tType v)
{
        value = v;
        left = NULL;
        right = NULL;
        counter = 0;
}
//***************************************************************
tNode::~tNode(void)
{
        // We don't have to do anything
        // But it has come to my attention that these are important.
}
//***************************************************************
//tTree Functions
// Construct / Destruct
tTree::tTree(void)
{
        root = NULL;    // Very important
}
//***************************************************************
tTree::~tTree(void)
{
        destroy(root);
}
//***************************************************************
// Private member functions
void tTree::destroy(tNode* current)
{
        if (current->left) destroy(current->left);
        if (current->right) destroy(current->right);
        delete current;
}
//***************************************************************
void tTree::rInsert(tNode** current, tNode* newNode)
{
        if (!*current)              // If there is no tree yet
        {
            *current = newNode;     // Create first node
            (*current)->counter++;  //  Increment counter for that word
        }
        else if (newNode->value < (*current)->value)    // If there is a tree
        {
            rInsert(&(*current)->left, newNode);        // If smaller value, place in left tree node
        }
        else if (newNode->value > (*current)->value)
        {
            rInsert(&(*current)->right, newNode);       // If larger value, place in right tree node
        }
        else if(newNode->value == (*current)->value)    // If words are the same
        {
            (*current)->counter++;                      //  Increment counter for that word
        }
}
//***************************************************************
void tTree::rPrint(tNode* current)
{
        // The location of the cout will change the order
        // that the words are printed.  This is alphebetically.
        if (current->left) // Prints the left side of the tree
        {
            rPrint(current->left);
        }
        // Prints out formatted output
        cout << fixed;
        cout << setw(30) << current->value << setw(8) << current->counter
             << setw(10) << setprecision(3) << (current->counter/totalCounter)*100 << "%" << endl;
        // Now print the right half of the tree
        if (current->right)
            rPrint(current->right);
}
//***************************************************************
// Public member function definitions
void tTree::clear(void)
{
        destroy(root);              // Destroy the tree
        root = NULL;                // Set the root back to NULL
}
//***************************************************************
void tTree::print(void)
{
        if (root) rPrint(root);      // Print out the tree
}
//***************************************************************
void tTree::insert(tType newValue)
{
        tNode* newNode  = new tNode(newValue);
        if (!root)                              // If tree does not exist yet
        {
            root = newNode;                     // Create first node in tree
        }
        else rInsert(&root, newNode);           // If tree exists, insert new word

}
//***************************************************************
tType clean_up(tType x)
{
    // Convert word to lowercase
    int i = 0;              // Used to step through each word
    int temp = x.length();  // Holds value of each word's length
    while (i < temp)        // As long as we are in each word
    {

  if (alphabet.find(x[i] )!= string::npos)  // If char found is within string 'alphabet'

/* ((x[i] >= 'A' && x[i] <= 'Z' )||(x[i] >= 'a' && x[i] <= 'z' ))*/
        {
            if(isupper(x[i]))               // If it is a capital letter
            {
               x[i] = tolower(x[i]);        // Convert letter to lowercase
            }
            i++;                            // Move to next letter in word
        }
        else                                // If char found is not found within string 'alphabet'
        {
             x.erase(i, 1);                 // Erase that char from the string
             temp--;                        // Decrement the length of the word
        }
    }
    return x;   // Return stripped word to insert
}
Why this?
1
2
3
4
5
6
7
8
infile >> con_word;             // Get first word of input file

        while (infile)                  // While still in input file
        {
            myTree.insert(clean_up(con_word));// Add word to the list
            totalCounter++;             // Add to total counter
            infile >> con_word;         // Get next word
        }


Why do you get the first word without also counting it with totalCounter? Why are you using while (infile) instead of while (!infile.eof())? As for the spaces, I don't just happen to have a constitution laying around, but the spaces in the file should be ignored. I didn't see anything in your tree that popped out at me, so I don't believe there is anything there. How do you know there is spaces? Are they counted? Are they added to your total words counter?

Do you have what the correct output is supposed to be? But I'm glad that you're almost done. Must feel good, and it'll only feel better once you get this done.

Edit: One thing I just thought about, and I'm still learning trees/nodes, but the tree should look something like a tree, right? So at the nodes at the very end of the tree, would they possibly be holding spaces in them? Could they be messing up your answer?

To clarify, the little twigs on your trees have no more nodes coming off of them, so what's at the tip of them if it's not supposed to be a node? A NULL node?
Last edited on
Here is the output:
http://ideone.com/qtMqT

Why do you get the first word without also counting it with totalCounter?

Because I thought before you can ask to be sure you are IN the input file, you have to be in it. And then I pass that word to the insert function, so it does get counted.

Why are you using while (infile) instead of while (!infile.eof())? 

What's the difference? I thought it was the same thing, and this is easier, so that's how I always do it.

How do you know there is spaces? Are they counted? Are they added to your total words counter?

I know because, yes, they are counted. Hmmm, but I don't think they are added to my total words counter, actually. Since I don't have the correct output, I popped the Constitution file into Word and did a word count. The count DOES match my count here in the program. But that first line in the output file shows 105 blanks. At least I think they are blanks, but maybe you're right and they are NULLs from the leaves in the tree?
Ugh, I just typed this long thing up for you, and my browser crashed -.-

Anyways, maybe the 105 is periods or returns or the "NULL" leaves. I also don't believe there is the word "d" or "httpwww..." in the Constitution.

I suggest that if you don't want to use .eof(), use .good(). When I look over old code and see .eof() in a while loop I automatically know I'm reading til the end of a file. but if I just see a variable, my first assumption is to think it's a bool.

As for when I asked you about reading in your first word, I was trying to suggest putting it in the while loop. Right now, I don't believe that you're actually counting your last word.

The last suggestion I have is to try typing up a short .txt file and see if your tree reads it correctly. If not, then you know to look at your tree. If it does, then you know there is an issue in the .txt file.

Hope this helps.
I'm not getting any issues with your program.

To clarify, the little twigs on your trees have no more nodes coming off of them, so what's at the tip of them if it's not supposed to be a node? A NULL node?


Exactly. The tNode constructor makes the left and right nodes NULL (which is defined as 0). So when functions use if (current->left) this only is true if a node has been inserted there.

rPrint() is only called with valid nodes. Note that print() ensures that root exists.
Last edited on
Topic archived. No new replies allowed.
Pages: 12