Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

IO binary stream and user defined classes.

76 views
Skip to first unread message

Christophe Bourez

unread,
May 4, 1997, 3:00:00 AM5/4/97
to

Hi,

*** please ***
*** reply to both ***
*** this newsgroup and bou...@tcts.fpms.ac.be ***

Iostream classes as been designed to use easily them with
user defined classes. One has to define the operator>> and
operator<< with adequate stream class as parameter types.
Nice!
Conceptually, iostream operators works with formatted I/O.
=========
example of code:
----------------
class MyClass
{
friend ostream& operator<<(ostream &os, MyClass &);
friend istream& operator>>(istream &os, MyClass &);
...
};

What about binary streams ?

I would like to develop classes which enable to read
and write formatted and unformatted (or binary) data.

What should I write for binary input/output ?

1. Functions read and write with adequate stream ?

example of code:
----------------
class MyClass
{
friend ostream& operator<<(ostream &, MyClass &);
friend istream& operator>>(istream &, MyClass &);
int read(istream &);
int write(ostream &);
...
};

Or :

2. Use permanent streams classes that define operator<< and >> ?
Is there a standard ?
Should I re-write a permanent stream classes ?
(In this event simple interface code is welcome)

3. What about STL input/output classes ?

4. What about mixed data (formatted+binary) : a class which
read from/write to a file objects with both formatted data
and binary data ?

=> What should be designed, in your opinion ?

Thanks in advance,

christophe.


[ Send an empty e-mail to c++-...@netlab.cs.rpi.edu for info ]
[ about comp.lang.c++.moderated. First time posters: do this! ]

Dietmar Kuehl

unread,
May 7, 1997, 3:00:00 AM5/7/97
to

Hi,
Christophe Bourez (bou...@tcts.fpms.ac.be) wrote:
: Conceptually, iostream operators works with formatted I/O.
: =========

In some sense, you want binary I/O also to be formatted: Writing them
just as the bits are found on some system is hardly desired for any
data. You will loose all your data if the next release of your compiler
chooses to use a different representation, eg. big endian instead of
little endian, or if you move to another platform. Thus, you should
think of binary I/O also to be formatted, just with a format which is
more efficient to read for machines and close to unreadable for
humans.

: What about binary streams ?

IOStreams consists of two major parts:

- an abstraction from the external representations which is formed by
'streambuf' and classes derived thereof

- a convenient frontend for formatted, human readable I/O, namely the
classes 'ostream' and 'istream'

(actually, the classes mentioned are special instantiations of
templates classes; however, I stick to these because it is more
convenient and the stuff basically applies to other instantiations,
too, although I think that it is reasonable to use the special case of
'char' for binary I/O).

Since I have the impression that IOStreams are well designed, I think
it is reasonable to mirror the design of the IOStream classes for
binary I/O. In doing so, as much as possible should be reused. Since
'istream' and 'ostream' are mainly tailored to be used with human
readable I/O, I think these classes cannot be reused for binary I/O.
However, the abstraction of the external representation, ie. the
hierarchy of classes rooted at 'streambuf' can be reused (at least as
long as the derived classes are used for something which is human
readable again, like eg. a 'streambuf' which writes to a GUI window).

Thus, I would use new classes, say 'ibstream' and 'obstream' which
define extractor and insertors for built-in types writing the bytes to
a 'streambuf'. For convenient construction of binary streams writing to
files, strings, etc. there may be derived classes like 'ibfstream' and
'obfstream', but classes derived from 'ibstream' and 'obstream' should
restrict their functionality to convenient construction of and access
to the used 'streambuf'.

That far, copying the design of IOStreams was straight forward. What
remains is a decision what to do in the insertors and extractors:
Merely writing the sequence of bytes used to represent an objects is
insufficient, especially if you are working on a heterogenous network
of computers. Thus, it has to be decided how the different objects have
to represented. A potential representation is the "eXternal Data
Representation" (XDR) which defines the size of types, the endianness,
the order of bits in floating point data, etc. Other representations
may also be reasonable. In any case, you should make sure that the
representation is defined such that it can be used on different
platforms.

For a sample implementation of binary IOStreams have a look at
<ftp://ftp.informatik.uni-konstanz.de/pub/algo/personal/kuehl/binio.tar.g
z>.
Of course, this implementation is basically what I have described
above. It should be fairly straight forward to use...

: 1. Functions read and write with adequate stream ?

: example of code:
: ----------------
: class MyClass
: {
: friend ostream& operator<<(ostream &, MyClass &);
: friend istream& operator>>(istream &, MyClass &);

BTW, I would rather use 'ostream &MyClass::print(ostream &)'
(correspondingly for input) instead of friend functions but this is a
matter of tastes.

: int read(istream &);
: int write(ostream &);

Like I outlined above, I would not use 'istream' and 'ostream' with
binary I/O. Thus, the function might look like this:

int read(ibstream &);
int write(ibstream &);

However, since this would require different uses for types which are
already designed to support this kind of I/O and other types like
built-in types and types from third party library, I prefer the use of
some operators, namely 'operator<<()' and 'operator>>()'. This also
make the code look more familiar... : ... : };

: 2. Use permanent streams classes that define operator<< and >> ?


: Is there a standard ?

I don't know whether this is standard but I think I would use this
approach (however, I don't know what you mean by "permanent streams").

: (In this event simple interface code is welcome)

For an example, have a look at the code I referenced above.
Potentially, you might even use this code instead of writing your own.
There is also a different implementation made available by Keith Davies
(kda...@pinc.com) under <http://www.coastnet.com/~darkblade>. However,
I haven't yet looked at the details of his approach (he also uses
overloaded operators for a new set of classes; however, he apparently
uses a different, more size efficient approach to the representation).

: 3. What about STL input/output classes ?

I doubt that there is a reasonable abstraction and a generic
implementation for binary I/O. Also, there are too many choices of the
exact behavior for binary I/O, especially with the represenation, that
I think it would not be reasonable to bundle it into the C++ standard.
Maybe there emerges a broadly used approach that the next revision of
the C++ standard includes binary I/O but I doubt that this would be the
case!

: 4. What about mixed data (formatted+binary) : a class which


: read from/write to a file objects with both formatted data
: and binary data ?

Since you can use the same 'streambuf' for both binary and human
readable I/O, you can also mix both: The frontend classes do no
buffering. All buffering is done by the 'streambuf'. Thus, you can mix
both types by just using the corresponding frontend at the right time.
However, I doubt that there is much utility of this approach... (but
then, eg. if the floating point representations differ, it may be the
easiest approach to convert between different representations).
--
<mailto:dietma...@uni-konstanz.de>
<http://www.informatik.uni-konstanz.de/~kuehl/>
I'm looking for an employment - See my homepage for details

0 new messages