2

So, i ran this program and the answer i expected was 26 but got -52 instead. Please explain why the code is reading the character incorrectly.

char x = 26; ofstream ofile("file.txt"); ofile << x; ifstream ifile("file.txt"); char y; ifile >> y; cout << (int)y; 
3
  • Did you do any error checking to make sure the I/O succeeded? Commented Jul 25, 2020 at 6:14
  • 2
    You might also want to open the files in binary mode. Closing the output file before opening the input file is also likely a good idea Commented Jul 25, 2020 at 6:18
  • Please provide a minimal reproducible example. Commented Jul 25, 2020 at 6:22

3 Answers 3

4

If you want to write non-text data, you should open the file in binary mode:

ofstream ofile("file.txt", ios_base::binary); 

A good practice is to check if the file was actually opened successfully:

ofstream ofile("file.txt", ios_base::binary); if (!ofile) return -1; 

Until you close the file, there's a high chance the buffer is not flushed, so there's no point in reading the file in another stream before you close it:

ofile << x; ofile.close(); 

A good idea is to finish the output to cout with endl:

cout << (int) y << endl; 

So you need something like:

#include <iostream> #include <fstream> using namespace std; int main() { char x = 26; ofstream ofile("file.txt", ios_base::binary); if (!ofile) return -1; ofile << x; ofile.close(); ifstream ifile("file.txt", ios_base::binary); if (!ifile) return -1; char y; ifile >> y; cout << (int) y << endl; ifile.close(); return 0; } 
Sign up to request clarification or add additional context in comments.

2 Comments

.close() will flush any remaining data to the file. endl will also, but see std::endl Notes section for a few considerations.
endl is not normally better than a simple new line, it is not necessary to flush most terminals which are line buffered anyway
3

When you write to an ofstream the data you've written isn't written directly to the file but held into an in memory buffer, the buffer will only be written to the file when the buffer is full, you seek the stream, flush the stream or close the stream.

Also note that if you aren't writing plain text it is safer to open the file in binary mode to ensure your exact data is read/written. You should also use read and write rather than the formatted i/o functions (or get and put for single characters).

It is also a good idea to add some error checking.

char x = 26; ofstream ofile("file.txt", std::ios_base::binary); ofile.put(x); if (!ofile) { std::cout << "write failed\n"; return; } ofile.close(); ifstream ifile("file.txt", std::ios_base::binary); char y; ifile.get(y); if (!ifile) { std::cout << "read failed\n"; return; } cout << (int)y << "\n"; 

Having tested on Windows the two required changes are

  1. Opening ifile in binary mode
  2. Closing/flushing ofile before opening iflie

Comments

1

This does what you want.

 char x = 26; ofstream ofile("file.txt"); ofile << x; ofile.close (); // <- closing the file ifstream ifile("file.txt"); char y; ifile >> y; cout << "Value: " << (int)y << endl; return 0; 

In this case it you may be reading something that's not yet written to disk (due to buffering.)

Output:

manuel@desktop:~/projects$ g++ -Wall -Wextra -g main.cc -o main -Wpedantic && ./main Value: 26 manuel@desktop:~/projects$ hexdump file.txt 0000000 001a 0000001 

2 Comments

i'm using MSVC compiler and still getting -52 instead of 26
@AkshitBansal Ups! Not a MS user sorry. It shouldm't behave like you say even in Windows though.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.