473,657 Members | 2,463 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

std::istream::r eadsome


What I would like to do is read bytes from a stream, any number and any
time. I would like it to wait until there are any bytes to read.

I want the exact same functionality as cstdio's "fread" but in a
std::istream.

It appeared at first that "readsome" would do exactly what I wanted but
it appears not to work very well at all (at least with gcc!). When
reading from a named pipe on gcc, it returns immediately - no errors,
just immediate return, is that the expected behaviour ?

Oct 28 '06 #1
13 10980
Hello Gianni!
Gianni Mariani wrote:
What I would like to do is read bytes from a stream, any number and any
time. I would like it to wait until there are any bytes to read.
There is no such functionality - neither in the C library no in the C++
library.
At least, these libraries are not required to do anything like this.
I want the exact same functionality as cstdio's "fread" but in a
std::istream.
You can use std::istream::r ead() for this. This will, however, block
until
either end of the input stream is reached or the requested number of
characters is received - as is the case for fread(), of course. If the
fread() on your system returns differently than described above, it is
either wrong or you are not using it on files. In the latter situation,
you
are relying on system specific features and the C or C++ standards
make no requirements on the behavior of the calls whatsoever.
It appeared at first that "readsome" would do exactly what I wanted
This is rather unlikely: the default implementation of readsome() just
obtains characters which are in the buffer of the underlying stream
buffer.
If there are none, it just returns, indicating that it read no
characers. The
default implementation does never attempt to read any bytes. Classes
derived from std::streambuf can choose to use a different approach but
none of the standard stream buffers does.
When
reading from a named pipe on gcc, it returns immediately - no errors,
just immediate return, is that the expected behaviour ?
Yes: there are no characters, i.e. there is nothing to do. You might
want to check gcount() for the number of characters read.

Good luck, Denise.

Oct 29 '06 #2
Denise Kleingeist wrote:
Hello Gianni!
Gianni Mariani wrote:
>What I would like to do is read bytes from a stream, any number and any
time. I would like it to wait until there are any bytes to read.

There is no such functionality - neither in the C library no in the C++
library.
I beg to differ. std::fread does exactly what I want.
At least, these libraries are not required to do anything like this.
These libraries have been performing exactly this way since I wrote my
first C program over 25 years ago. I have no idea what you talk about.
>
>I want the exact same functionality as cstdio's "fread" but in a
std::istream .

You can use std::istream::r ead() for this. This will, however, block
until
either end of the input stream is reached or the requested number of
characters is received - as is the case for fread(),
Unfortunately, this is not the case, a call to std::istream::r ead will
fail if there is not enough data to fulfill the read request. There is
no way for the istream::read call interface to indicate that it has read
fewer than the requested number of bytes so the last block read will
almost always be unreadable.

of course. If the
fread() on your system returns differently than described above, it is
std::fread does operate exactly as I want. The size of the last block
being read is returned. I want to do the same thing with std::istream.

.... snip
>It appeared at first that "readsome" would do exactly what I wanted

This is rather unlikely: the default implementation of readsome() just
obtains characters which are in the buffer of the underlying stream
buffer.
If there are none, it just returns, indicating that it read no
characers. The
default implementation does never attempt to read any bytes. Classes
derived from std::streambuf can choose to use a different approach but
none of the standard stream buffers does.
That's strange since at least 2 compilers I use do exactly the opposite
of what you say, on regular files no less.
>
>When
reading from a named pipe on gcc, it returns immediately - no errors,
just immediate return, is that the expected behaviour ?

Yes: there are no characters, i.e. there is nothing to do. You might
want to check gcount() for the number of characters read.
OK - you have affirmed why keep away from iostreams for C++ io. It's
not only I who can't figure out how to use it properly.
Oct 29 '06 #3

Gianni Mariani wrote in message ...
>
It appeared at first that "readsome" would do exactly what I wanted but
it appears not to work very well at all
Yeah, know what you mean. I used to readsome, then codesome. It was always
the codesome that would "Git 'er done!".

--
Bob <GR
POVrookie
Oct 29 '06 #4
Hello Gianni!
Gianni Mariani wrote:
Denise Kleingeist wrote:
Gianni Mariani wrote:
What I would like to do is read bytes from a stream, any number and any
time. I would like it to wait until there are any bytes to read.
There is no such functionality - neither in the C library no in the C++
library.

I beg to differ. std::fread does exactly what I want.
OK. I'm assuming I know what you want and I'm certain that this doesn't
work
in either C or C++. Since you disagree, apparently my assumption is
wrong.
Now, lets verify or falsify my assumptions: from the description given
and the
mention of pipes, I assume you want to obtain whatever amount of data
is
available from your source as soon as it becomes available. For
example, if
you had read all available character, you want to wait until new
characters
become available. Say you are using a buffer of 64 characters and 25
become
available, you want the read function to return and report that 25
characters
have become available.

Functionality like this can be implemented on many systems supporting C
or
C++ but neither language provides the necessary facilities to set this
up: you
need to resort to platform specific functionality to do so.
At least, these libraries are not required to do anything like this.

These libraries have been performing exactly this way since I wrote my
first C program over 25 years. I have no idea what you talk about.
I'm talking about C and C++ standards and what I assume you want to do.
Neither C nor C++ offer functionality which reads characters and
returns
whatever is there without hitting EOF or an error. Both standards
define their
I/O operations to either read precisely the number of characters
specified in
their read operations, hit an error, or reach EOF. Neither standard
defines any form of reads which wait until there are characters
available and
just return those. ... unless, of course, EOF is reached or an error is
encountered.
If you disagree, please point me at the section of the C or C++
standard which
states otherwise. For C, I'm looking at 7.19.8.1 (The fread function),
for C++ at
27.6.1.3 (lib.istream.un formatted) paragraph 30.
I want the exact same functionality as cstdio's "fread" but in a
std::istream.
You can use std::istream::r ead() for this. This will, however, block
until
either end of the input stream is reached or the requested number of
characters is received - as is the case for fread(),

Unfortunately, this is not the case, a call to std::istream::r ead will
fail if there is not enough data to fulfill the read request. There is
no way for the istream::read call interface to indicate that it has read
fewer than the requested number of bytes so the last block read will
almost always be unreadable.
There is a way to find out how many characters std::istream::r ead() has
read:
std::istream::g count() provides the number of characters read by the
last
unformatted input function (27.6.1.3, lib.istream.unf ormatted,
paragraph 1).
of course. If the
fread() on your system returns differently than described above, it is

std::fread does operate exactly as I want. The size of the last block
being read is returned. I want to do the same thing with std::istream.
If you want a function which returns the number of characters read
rather
than using std::istream::g count() to determine this number, you can use
std::streambuf: :sgetn(), e.g.:

std::streamsize n = std::cin.rdbuf( )->sgetn(buffer , size);

(see 27.5.2.2.3, lib.streambuf.g et.area, paragraph 6, and 27.4.4.2,
lib.basic.ios.m embers, paragraph 4).
... snip
It appeared at first that "readsome" would do exactly what I wanted
This is rather unlikely: the default implementation of readsome() just
obtains characters which are in the buffer of the underlying stream
buffer.
If there are none, it just returns, indicating that it read no
characers. The
default implementation does never attempt to read any bytes. Classes
derived from std::streambuf can choose to use a different approach but
none of the standard stream buffers does.

That's strange since at least 2 compilers I use do exactly the opposite
of what you say, on regular files no less.
Well, maybe I should have said that std::filebuf is not required to
provide a
different than the default implementation of std::streambuf: :in_avail()
which
is the function used to determine the maximum number of characters
available to std::istream::r eadsome(). In my experience, std::filebuf
does
not provide a different implementation than the default and thus
readsome()
which just read the characters currently stuck in the buffer. Since
your
impression was that readsome() didn't work for gcc, I'd guess that at
least
libstdc++ uses does not override this function.
When
reading from a named pipe on gcc, it returns immediately - no errors,
just immediate return, is that the expected behaviour ?
Yes: there are no characters, i.e. there is nothing to do. You might
want to check gcount() for the number of characters read.

OK - you have affirmed why keep away from iostreams for C++ io. It's
not only I who can't figure out how to use it properly.
I certainly know how to use it properly! ... and I'm certainly not
using stdio
in any code I write although I know that library better than most
others, too.
stdio has too many problems, IMO.

Good luck, Denise.

Oct 29 '06 #5

Hi Denise, I know you're trying to help so I appreciate that but I
don't think you really understand the full extent of the question. Also
the format of your text with the uneven breaks in the lines makes it
hard to read on my newsreader.

Let me rephrase the question.

I want to read all the data from a file until end of file a chunk at a
time using std::istream.

Sounds simple enough right ?

Well there does not seem to be any way to do this easily.

std::istream::r ead is incapable of reading the last incomplete block.

std::istream::r eadsome looks like the right answer, but alas it does not
wait for data from pipes.

So, how do you do it ? Read just the bytes from the file block by block
to an uneven block end for any kind of file (including pipes) in a
standard C++ way.
Oct 29 '06 #6
Hi Gianni!
Gianni Mariani wrote:
Hi Denise, I know you're trying to help so I appreciate that but I
don't think you really understand the full extent of the question.
This could indeed be the problem...
Also
the format of your text with the uneven breaks in the lines makes it
hard to read on my newsreader.
I'm sorry about this: I'm using Google Groups to post and
this keeps messing up my formatting.
Let me rephrase the question.
Precisions is always good: no guessing this time :-)
I want to read all the data from a file until end of file a chunk at a
time using std::istream.

Sounds simple enough right ?
That is simple, indeed! Where is your problem then? Here is
the code to do it (plus writing the result to standard out;
of course, you want to add error some error handling on the
program arguments and opening the file):

#include <fstream>
#include <iostream>

int main(int ac, char *av[])
{
std::ifstream in(av[1]);
char buffer[64];
while (in.read(buffer , sizeof(buffer)) )
std::cout.write (buffer, sizeof(buffer)) ;
// process the final chunk:
std::cout.write (buffer, in.gcount());
}
Well there does not seem to be any way to do this easily.
Doesn't look too complicated to me...
std::istream::r ead is incapable of reading the last incomplete block.
Of course, it is not! That would be pretty lame!
std::istream::r eadsome looks like the right answer, but alas it does not
wait for data from pipes.
std::istream::r eadsome() is intended to do a non-blocking
read of data which is guaranteed to be available at the time
of the call. Basically, the only data which can normally be
guaranteed is the data in the stream buffer's internal buffer
and the default implementation of the associated functionality
(the stream buffer method in_avail()) just looks at the stream
buffer's buffer. Classes derived from std::streambuf can
override in_avail() to do a better job but few classes really
do. However, this is not what you want for the question above.
So, how do you do it ? Read just the bytes from the file block by block
to an uneven block end for any kind of file (including pipes) in a
standard C++ way.
Of course, the C++ way to do the code I wrote above looks
more like the code below :-)

#include <fstream>
#include <iostream>
int main(int ac, char* av[])
{
std::cout << std::ifstream(a v[1]).rdbuf();
}

Good luck, Denise.

Oct 29 '06 #7
Denise Kleingeist wrote:
....
Of course, the C++ way to do the code I wrote above looks
more like the code below :-)

#include <fstream>
#include <iostream>
int main(int ac, char* av[])
{
std::cout << std::ifstream(a v[1]).rdbuf();
}
OK, now I get it. Bypass all the nonsense and get to the streambuf.

#include <iostream>

using namespace std;

int main ()
{

streambuf * pbuf = std::cin.rdbuf( );
char l_buffer[128];

streamsize i;

while ( i = pbuf->sgetn( l_buffer, sizeof(l_buffer ) ) )
{
std::cout.write ( l_buffer, i );
std::cout.flush ();
}

return 0;
}

This seems to behave like I expect it to.

The only last thing I would like is to be able to covert a non binary
file to a "std::ios::bina ry" file without closing it. The program reads
input from cin (optionally) and after reading the first few bytes it
determines if the file is a "binary" style file and then starts reading
in binary. The program currently reads past "\r\n" or "\n" or \n" and
"does the right thing". So it would be nice to be able to get a binary
handle on std::cin in particular.

G
Oct 29 '06 #8
Hello Gianni!
Gianni Mariani wrote:
OK, now I get it. Bypass all the nonsense and get to the streambuf.
That certainly wasn't what I was saying but there are many
approaches to obtain the desired goal.
The only last thing I would like is to be able to covert a non binary
file to a "std::ios::bina ry" file without closing it.
There is no way to do something like this with the standard
I/O function, neither in C nor in C++. I guess, that is part
of the reason why these flags are called "openmode" rather
than "streammode " or something like this. If you are on a
UNIX system there is nothing to do anyway: the file modes
simply don't differ.

Good luck, Denise.

Oct 29 '06 #9
Denise Kleingeist wrote:
Hello Gianni!
Gianni Mariani wrote:
>OK, now I get it. Bypass all the nonsense and get to the streambuf.

That certainly wasn't what I was saying but there are many
approaches to obtain the desired goal.
>The only last thing I would like is to be able to covert a non binary
file to a "std::ios::bina ry" file without closing it.

There is no way to do something like this with the standard
I/O function, neither in C nor in C++. I guess, that is part
of the reason why these flags are called "openmode" rather
than "streammode " or something like this. If you are on a
UNIX system there is nothing to do anyway: the file modes
simply don't differ.
The code is cross platform. I'd like to stick to as many standard C++
constructs as possible. I suspected that this was a stretch.

according to msdn this is all that it needs to do.
result = _setmode( _fileno( stdin ), _O_BINARY );
Oct 29 '06 #10

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

3
1882
by: Morten Rodal | last post by:
#include <iostream> #include <fstream> using namespace std; #ifndef BUFSIZ #define BUFSIZ 1024 #endif int main(int argc, char **argv) {
19
10306
by: Lionel B | last post by:
Greetings, I need to read (unformatted text) from stdin up to EOF into a char buffer; of course I cannot allocate my buffer until I know how much text is available, and I do not know how much text is available until I have read it... which seems to imply that multiple reads of the input stream will be inevitable. Now I can correctly find the number of characters available by: |
2
3707
by: Alex Vinokur | last post by:
Method istream::readsome() behaves in a different way with two different compilers: g++ and Microsoft C++. What is reason for that? Which compiler is correct? It seems that g++ is. ------ File xxx.cpp ------ #include <iostream> #include <fstream> #include <cassert>
3
12226
by: Mario | last post by:
Hello, I couldn't find a solution to the following problem (tried google and dejanews), maybe I'm using the wrong keywords? Is there a way to open a file (a linux fifo pipe actually) in nonblocking mode in c++? I did something ugly like --- c/c++ mixture --- mkfifo( "testpipe", 777);
18
8245
by: Amadeus W. M. | last post by:
I'm trying to read a whole file as a single string, using the getline() function, as in the example below. I can't tell what I'm doing wrong. Tried g++ 3.2, 3.4 and 4.0. Thanks! #include <iostream> #include <fstream> #include <cstdlib> #include <string>
5
1411
by: ashton | last post by:
Hello, I have a file (mytest.fle) it is just a text file with a different extension. I would like to be able to open this file through my C++ application and read it in as a string. For example, I would right click on this file, select open with, then navigate to my EXE to open this file.
2
14048
by: Karl | last post by:
Hey everyone! I've got a quick question on whether std::ifstream is buffered or not. The reason is that I have a homework assignment that requires me to benchmark copying files using different buffer sizes. I ended up doing this using std::istream::readsome() and std::ostream::write(): // now try writing to the destination file std::ifstream sourceStream(sourceFilename.c_str(), std::ios::binary);
5
10793
by: Noel Mosa | last post by:
Hi, i have an incoming object (file) on a istream. i need to pass it to another (C programmed!)module in a char* array and providing its size(also needing the size to mallocate the char* array). i used to get it using the tellg() function. but on some files this does not seem to work right. kinda like this:
16
8936
by: vizzz | last post by:
Hi there, i need to find an hex pattern like 0x650A1010 in a binary file. i can make a small algorithm that fetch all the file for the match, but this file is huge, and i'm scared about performances. Is there any stl method for a fast search? Andrea
0
8411
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main usage, and What is the difference between ONU and Router. Let’s take a closer look ! Part I. Meaning of...
0
8323
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
8838
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
0
8739
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven tapestry of website design and digital marketing. It's not merely about having a website; it's about crafting an immersive digital experience that captivates audiences and drives business growth. The Art of Business Website Design Your website is...
1
8513
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
1
6176
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new presenter, Adolph Dupré who will be discussing some powerful techniques for using class modules. He will explain when you may want to use classes instead of User Defined Types (UDT). For example, to manage the data in unbound forms. Adolph will...
0
4173
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
0
4329
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
2
1732
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.