Seg Fault problem with inFile.getline command

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
#include <iostream>
#include <fstream>
#include <string>
#include <cstdlib>
#include <iomanip>
using namespace std;

ifstream inFile( "textinput.txt", ios::in );
ofstream outFile( "textoutput.txt" , ios::out);

void initialArray( int * );
void characterCount( char, int *);
void copyText( char *, int * );

int main()
{
    char letter;
    char* line;
    int lineCount = 0;
    int letterCount[26];
    char alpha = 65;

    initialArray( letterCount );

    ifstream inFile( "textinput.txt", ios::in );
    ofstream outFile( "textoutput.txt" , ios::out);

    if ( !inFile || !outFile)
    {
        cerr << " One of the two files could not be openned to read or write" << endl;
        exit(1);
    }
     while( inFile )
    {
        inFile.getline( line, 80 );
        cout << 1 << line;
        copyText( line, &lineCount );
    }
    while( inFile >> letter )
        characterCount( letter, letterCount );

    while( inFile )
    {
        inFile.getline( line, 79 );
        cout << 1 << line;
        copyText( line, &lineCount );
    }

    cout << " The total number of lines in the text file is: " << lineCount <<endl;

    for( int i =0; i < 26; i++)
    {
        cout << "The number of " << alpha << ":" << setw(5) << letterCount[i] << endl;
        alpha++;
    }


}

void initialArray( int *letterCountPtr )
{
    for(int j = 0; j < 26; j++)
    letterCountPtr[j] = 0;
}

void characterCount( char currentLetter, int *letterCountPtr )
{
    currentLetter = (char)toupper( currentLetter );

    switch (currentLetter)
    {
        case 'A': letterCountPtr[0]++;
        break;
        case 'B': letterCountPtr[1]++;
        break;
        case 'C': letterCountPtr[2]++;
        break;
        case 'D': letterCountPtr[3]++;
        break;
        case 'E': letterCountPtr[4]++;
        break;
        case 'F': letterCountPtr[5]++;
        break;
        case 'G': letterCountPtr[6]++;
        break;
        case 'H': letterCountPtr[7]++;
        break;
        case 'I': letterCountPtr[8]++;
        break;
        case 'J': letterCountPtr[9]++;
        break;
        case 'K': letterCountPtr[10]++;
        break;
        case 'L': letterCountPtr[11]++;
        break;
        case 'M': letterCountPtr[12]++;
        break;
        case 'N': letterCountPtr[13]++;
        break;
        case 'O': letterCountPtr[14]++;
        break;
        case 'P': letterCountPtr[15]++;
        break;
        case 'Q': letterCountPtr[16]++;
        break;
        case 'R': letterCountPtr[17]++;
        break;
        case 'S': letterCountPtr[18]++;
        break;
        case 'T': letterCountPtr[19]++;
        break;
        case 'U': letterCountPtr[20]++;
        break;
        case 'V': letterCountPtr[21]++;
        break;
        case 'W': letterCountPtr[22]++;
        break;
        case 'X': letterCountPtr[23]++;
        break;
        case 'Y': letterCountPtr[24]++;
        break;
        case 'Z': letterCountPtr[25]++;
        break;
    }
}

void copyText( char *line, int *lineCount )
{

    cout << line << endl;
    outFile << line << endl;
    lineCount++;
}
Last edited on
You're trying to store some data in the memory location pointed to by the pointer line. Where does that pointer point? There's no way to know, because you never gave it a value; it's pointing into some random piece of memory somewhere, and the operating system then sees you trying to write over memory that isn't yours and stops you.

If you're going to write into the memory that line points to, you've got to actually ensure that it points somewhere sensible.

Last edited on
OK. So if I initialize the pointer line it still doesn't resolve it. I am unsure of the resolution and I have searched all through my book.
1
2
3
4
5
6
7
void copyText( char *line, int *lineCount )
{

    cout << line << endl;
    outFile << line << endl;
    lineCount++;
}


Did you mean:
1
2
3
4
5
6
7
void copyText( char *line, int *lineCount )
{

    cout << line << endl;
    outFile << line << endl;
    (*lineCount)++;
}

??


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
void characterCount( char currentLetter, int *letterCountPtr )
{
    currentLetter = (char)toupper( currentLetter );

    switch (currentLetter)
    {
        case 'A': letterCountPtr[0]++;
        break;
        case 'B': letterCountPtr[1]++;
        break;
        case 'C': letterCountPtr[2]++;
        break;
        case 'D': letterCountPtr[3]++;
        break;
        case 'E': letterCountPtr[4]++;
        break;
        case 'F': letterCountPtr[5]++;
        break;
        case 'G': letterCountPtr[6]++;
        break;
        case 'H': letterCountPtr[7]++;
        break;
        case 'I': letterCountPtr[8]++;
        break;
        case 'J': letterCountPtr[9]++;
        break;
        case 'K': letterCountPtr[10]++;
        break;
        case 'L': letterCountPtr[11]++;
        break;
        case 'M': letterCountPtr[12]++;
        break;
        case 'N': letterCountPtr[13]++;
        break;
        case 'O': letterCountPtr[14]++;
        break;
        case 'P': letterCountPtr[15]++;
        break;
        case 'Q': letterCountPtr[16]++;
        break;
        case 'R': letterCountPtr[17]++;
        break;
        case 'S': letterCountPtr[18]++;
        break;
        case 'T': letterCountPtr[19]++;
        break;
        case 'U': letterCountPtr[20]++;
        break;
        case 'V': letterCountPtr[21]++;
        break;
        case 'W': letterCountPtr[22]++;
        break;
        case 'X': letterCountPtr[23]++;
        break;
        case 'Y': letterCountPtr[24]++;
        break;
        case 'Z': letterCountPtr[25]++;
        break;
    }
}

Whoaaa, that was huge. Compress it to:
1
2
3
4
5
6
7
void characterCount( char currentLetter, int *letterCountPtr )
{
    currentLetter = (char)toupper( currentLetter );
    if(currentLetter < 'A' || currentLetter > 'Z')
        return;
    letterCountPtr[ (currentLetter - 'A') ]++;
}


1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <iostream>
#include <fstream>
#include <string>
#include <cstdlib>
#include <iomanip>
using namespace std;

ifstream inFile( "textinput.txt", ios::in );
ofstream outFile( "textoutput.txt" , ios::out);
//...
    initialArray( letterCount );

    ifstream inFile( "textinput.txt", ios::in );
    ofstream outFile( "textoutput.txt" , ios::out);

Wtf redeclaration? Remove the globals. They're not safe at all, being file streams.
1
2
3
4
int main()
{
    char letter;
    char* line;

Sorry, WHAT is line initialized to WHAT? line is NOT pointing to valid memory.
Change it like this:
1
2
3
4
int main()
{
    char letter;
    char line[512] = {0}; // line is pointing to 512 bytes of CLEAN memory. 
Last edited on
I am unsure of the resolution and I have searched all through my book.


Read about pointers.
http://www.cplusplus.com/articles/EN3hAqkS/
and
http://www.cplusplus.com/articles/z186b7Xj/
Thanks a lot ESS. that compressing it is awesome and I should have seen that. About the char *line. I was under the assumption you could use that as a string pointer. Thank moschops. I will try to work it out.
About the char *line. I was under the assumption you could use that as a string pointer.


You can use it as a pointer to a (c-style) string; you still have to actually create that string. Otherwise, what are you pointing at?
About the char *line. I was under the assumption you could use that as a string pointer.

A C++ (std) string isn't unlimited. But when you add some new content, its buffer size increases to allow you more space to put chars into. So, if you want a std::string with 512 bytes of buffer, you should push at least 512 characters into a string. Otherwise, the string's buffer size is less than 512, it's a dynamic buffer.
Let's say this:
1
2
3
4
5
6
string EmptyString; // EmptyString does not need any memory at this point.
//It will probably allocate one byte for the default null-terminator.
//EmptyString's char pointer at this point of time points to AT LEAST one byte of memory.
EmptyString >> "Text"; // Now, the string needs some more memory.
//So it allocates other 4 characters, and copies the old 1-byte buffer into the new 5-byte buffer.
//Now EmptyString's char pointer at this point of time points to AT LEAST five bytes of memory. 

Hope you understand such things. ^
Topic archived. No new replies allowed.