Berkeley CSUA MOTD:Entry 27833
Berkeley CSUA MOTD
 
WIKI | FAQ | Tech FAQ
http://csua.com/feed/
2025/05/28 [General] UID:1000 Activity:popular
5/28    

2003/3/25-26 [Computer/SW/Languages/C_Cplusplus] UID:27833 Activity:high
3/24    I have not been using C/C++ for the last 5 years.  I am wondering if
        there's something like the Perl De/Serializer for C/C++.
           \_ What about something like ResourceBundle in Java?
        \_ of course not. mabye you should take a civics class, you ignorant
           liberal stooge.
                \_ Problems with your self-esteem?  Mommy and daddy too mean?
                   \_ ignore him, his penis too smal, that must be it.
                        \_ what does any of this crap have to do with the OP's
                           question?
           \_ What about something like ResourceBundle in Java?
        \_ Take a look at the following:
           http://www.parashift.com/c++-faq-lite/serialization.html
           http://xparam.sourceforge.net/guide
2025/05/28 [General] UID:1000 Activity:popular
5/28    

You may also be interested in these entries...
2011/3/7-4/20 [Computer/SW/Languages/C_Cplusplus] UID:54056 Activity:nil
3/7     I have a C question.  I have the following source code in two identical
        files t.c and t.cpp:
                #include <stdlib.h>
                int main(int argc, char *argv[]) {
                  const char * const * p1;
                  const char * * p2;
	...
2010/6/4-30 [Computer/SW/Languages/C_Cplusplus] UID:53849 Activity:nil
6/4     Is this valid C++ code?
        std::string getStr(void) {
            std::string str("foo");
            return str;
        }
        void foo(char *s);
	...
2006/8/25-28 [Computer/SW/Languages/C_Cplusplus] UID:44153 Activity:nil
8/25    Dear C++ experts. Why would there be two "const" in the following
        method declaration?
        const bool ILikeMotd() const;
        \_ The first const refers to the data type returned.  The second
           const says the function doesn't modify an object's member variables.
           The first const in your example is bad, I believe; it should
	...
2006/7/28-8/2 [Computer/SW/Languages/C_Cplusplus] UID:43824 Activity:nil
7/27    In C/C++, how come some parameters have "mconst" before the type
        and some don't? I don't see how it changes anything. -newbie
        \_ If it's a pointer or reference, then you can't change the contents.
        \_ Nicely summarized here:
           http://www.parashift.com/c++-faq-lite/const-correctness.html
        \_ The answer is 47. -proud American
	...
2006/5/10-11 [Computer/SW/Languages/C_Cplusplus] UID:43010 Activity:nil
5/10    I'm trying to port a small project from builsing with MS Visual Studio
        to GCC in MinGW on windows.  Only 1 line is having a compile error.
        Using STL, the line
        if(hashmap->find(key)!=0)
        Has the following error:
        no match for `std::_Rb_tree_iterator<std::pair<const std::string, int>,
	...
2006/2/13-20 [Recreation/Computer/Games] UID:41824 Activity:moderate
2/13    What are your favorite old school computer games?
        \_ Recently rediscovered Pathways into Darkness http://pid.bungie.org
           \_ The skill levels for weapons was a cool innovation for a fps.
        \_ BEYOND CASTLE WOLFENSTEIN
        \_ Jumpman Jr.
        \_ The Pawn (C64 - 1985?), Conan (various 1986?)
	...
Cache (8192 bytes)
www.parashift.com/c++-faq-lite/serialization.html
It lets you take an object or group of objects, put them on a disk or send them through a wire or wireless transport mechanism, then later, perhaps on another computer, reverse the process: resurrect the original object. The basic mechanisms are to flatten object into a one-dimensional stream of bits, and to turn that stream of bits back into the original object. There are lots and lots (and lots) of if's, and's and but's, and in reality there are a whole continuum of techniques with lots of dimensions. Because I have a finite amount of time (translation: I don't get paid for any of this), I've simplified it to a 23 decision between using human-readable ("text") or non-human-readable ("binary") format, followed by a list of five techniques arranged more-or-less in increasing order of sophistication. You are, of course, not limited to those five techniques. You will probably end up mixing ideas from several techniques. And certainly you can always use a more sophisticated (higher numbered) technique than is actually needed. In fact it might be wise to use a more sophisticated technique than is minimally needed if you believe future changes will require the greater sophistication. Later FAQs show 25 how to write simple types in text format and 26 how to write simple types in binary format. Here's that same information arranged like an algorithm: 1. The first step is to 41 make an eyes-open decision between text- and binary-formats. If your objects aren't part of an inheritance hierarchy and don't contain pointers, 42 use solution #1. Else if your objects don't contain pointers to other objects, 43 use solution #2. Else if the 44 graph of pointers within your objects contain neither 45 cycles nor 46 joins, 47 use solution #3. Else if the 48 graph of pointers within your objects don't contain 49 cycles and if the only 50 joins are to terminal (leaf) nodes, 51 use solution #4. Remember: feel free to mix and match, to add to the above list, and, if you can justify the added expense, to use a more sophisticated technique than is minimally required. One more thing: the issues of inheritance and of pointers within the objects are logically unrelated, so there's no theoretical reason for #2 to be any less sophisticated than #3-5. However in practice it often (not always) works out that way. So please do not think of these categories as somehow sacred -- they're somewhat arbitrary, and you are expected to mix and match the solutions to fit your situation. This whole area of serialization has far more variants and shades of gray than can be covered in a few questions/answers. Here are a few of the pros/cons of human-readable ("text") format vs. However that is relevant only if your application is CPU bound and you intend to do serialization and/or unserialization on an inner loop/bottleneck. Remember: 90% of the CPU time is spent in 10% of the code, which means there won't be any practical performance benefit unless your "CPU meter" is pegged at 100%, and your serialization and/or unserialization code is consuming a healthy portion of that 100%. The important thing to remember is that one size does not fit all -- make a careful decision here. One more thing: no matter which you choose, you might want to start each file / stream with a "magic" tag and a version number. That way if you decide to make a radical change in the format, you hopefully will still be able to read the output produced by the old software. The answer depends on 63 your decision regarding human-readable ("text") format vs. The primitives discussed in those FAQs will be needed for most of the other FAQs in this section. Before you read this, make sure to 71 evaluate all the tradeoffs between human-readable and non-human-readable formats. The tradeoffs are non-trivial, so you should resist a knee-jerk reaction to do it the way you did it on the last project -- one size does not fit all. After you have made an eyes-open decision to use human-readable ("text") format, you should remember these keys: * You probably want to use iostream's >> and << operators rather than its read() and write() methods. The >> and << operators are better for text mode, whereas read() and write() are better for binary mode. One simple approach is to always add a space (' ') before each number, that way the number 1 followed by the number 2 won't run together and look like a 12. Since the leading space will automatically get soaked up by the >> operator, you won't have to do anything explicit to extract the leading space in the code that reads things back in. You can't unambiguously terminate all strings with a '\n' or '"' or even '\0' if some string might contain those characters. After this transformation, you can either make strings go until end-of-line (meaning they are deliminated by '\n') or you can delimit them with '"'. In particular, if you open a std::fstream without std::ios::binary, some operating systems translate end-of-line characters. Note that this can make it hard for people to read/write the file, since the value just after that might not have a visible separator, but you still might find it useful. Please remember that these are primitives that you will need to use in the other FAQs in this section. Before you read this, make sure to 77 evaluate all the tradeoffs between human-readable and non-human-readable formats. The tradeoffs are non-trivial, so you should resist a knee-jerk reaction to do it the way you did it on the last project -- one size does not fit all. After you have made an eyes-open decision to use non-human-readable ("binary") format, you should remember these keys: * Make sure you open the input and output streams using std::ios::binary. Do this even if you are on a Unix system since it's easy to do, it documents your intent, and it's one less non-portability to locate and change down the road. That header should define inline functions like readNetworkInt(std::istream& istr) to read a "network int," and so forth for reading and writing all the primitive types. You can define the format for these pretty much anyway you want. Note: the floating point differences are the most subtle and tricky to handle. It can be done, but you'll have to be careful with things like 78 NaN, over- and under-flow, #bits in the mantissa or exponent, etc. The simplest is to store small numbers in a smaller number of bytes. For example, to store an unsigned integer in a stream that has 8-bit bytes, you can hijack the 8th bit of each byte to indicate whether or not there is another byte. If the average number is smaller than around half a billion, this will use less space than storing every four-byte unsigned number in four 8-bit bytes. You can't unambiguously terminate all strings with a '\0' if some string might contain that character; The easiest solution is to write the integer length just before the string data. Make sure the integer length is written in "network format" to avoid sizeof and endian problems (see the solutions in earlier bullets). Please remember that these are primitives that you will need to use in the other FAQs in this section. This is the least sophisticated problem, and not surprisingly, it is also the least sophisticated solution: * Every class should handle its own serialization and unserialization. You will typically create a member function that serializes the object to some sink (such as a std::ostream), and another that allocates a new object, or perhaps changes an existing object, setting the member data based on what it reads from some source (such as a std::istream). The version number simply represents the serialized format; This means the version numbers don't need to be fancy -- they usually don't need a major and minor number. Suppose you want to serialize a "shape" object, where Shape is an abstract class with derived classes Rectangle, Ellipse, Line, Text, etc. You would declare a 91 pure virtual function serialize(std::ostream&) const within class Shape, and make sure the first thing done by each override is to write out the class's identity. For example, Ellipse::serialize(std::ostream&) const would write out the identifier Ellipse (perhaps 92 as a...
Cache (104 bytes)
xparam.sourceforge.net/guide -> xparam.sourceforge.net/guide/
Introduction Previous: Up: Library and Documentation by Ronnie Maor & Michael Brand Table of Contents 1.