2

When I search using keywords of 'fgets' and 'newline', there are many posts regarding how to remove the trailing newline character (and such removal appears to be a burden). Yet it seems there is few explaination on how that newline is necessary for fgets to include. Also in C++, the 'std::getline' and 'std::istream:getline' methods will not keep the newline character. So is there a reason for it?

Lyn
  • 699
  • 1
  • 7
  • 17
  • 1
    There's probably not any exceptional argument for why the original authors of C decided to include the newline character. It just is - it's what fgets() does. If the newline wasn't included, there would be someone else asking why it isn't included. – nos Oct 31 '14 at 10:21
  • 1
    Thanks nos. I can take it as by design, just personally feel that it might not be a good one. – Lyn Oct 31 '14 at 10:26
  • Note: `fgets()` will happily read and put in its buffer embedded `'\0'` and thus read 6 `char` and form a buffer like `'A'`, `'B'`, `'C'`, `'\0'`, `'D'`, `'\n'`, `'\0'`. Suspect `std::istream:getline` also nicely reads embedded `'\0'`. IMO, `fgets()` not returning the length read is a greater deficiency. `strlen()` is insufficient as it does accurately report the data read by `fgets()` in all cases. – chux - Reinstate Monica Oct 31 '14 at 13:20

2 Answers2

3

Here is satisfying (IMHO) explanation:
http://www.cplusplus.com/reference/cstdio/fgets/

Especially:

A newline character makes fgets stop reading, but it is considered a valid character by the function and included in the string copied to str.

4rlekin
  • 748
  • 5
  • 16
  • thanks for your comment. So it`s by design as "it is considered a valid character by the function and included in the string copied to str.". But this design drives people trying hard to remove the newline char, and C++ counterparts do not follow this design. – Lyn Oct 31 '14 at 10:23
  • 3
    @Lyn But if it was removed, some other people would have to try hard to *preserve* the newline. People have different needs. And what C++ does, is not really relevant; Those are 2 different languages with different goals. – user694733 Oct 31 '14 at 10:25
2

No, it's not necessary but if present it will be included in the returned line.

The manual page says:

Reading stops after an EOF or a newline. If a newline is read, it is stored into the buffer. A terminating null byte ('\0') is stored after the last character in the buffer.

So that's why it behaves that way.

Note that you can't assume that there will be a newline last in the buffer, you must check before removing it otherwise you risk truncating the last line if it didn't have a newline.

unwind
  • 391,730
  • 64
  • 469
  • 606