November 2005
Beginner to intermediate
594 pages
16h 23m
English
You need the basic class copy operations—copy construction and assignment—to be exception-safe.
Employ the tactics discussed in Recipe
9.4 by doing everything that might throw
first, then changing the object state with operations that can’t throw only after the hazardous work is complete. Example 9-6 presents the Message class again, this time with the assignment operator
and copy constructor defined.
Example 9-6. Exception-safe assignment and copy construction
#include <iostream> #include <string> const static int DEFAULT_BUF_SIZE = 3; const static int MAX_SIZE = 4096; class Message { public: Message(int bufSize = DEFAULT_BUF_SIZE) : bufSize_(bufSize), initBufSize_(bufSize), msgSize_(0), key_("") { buf_ = new char[bufSize]; // Note: now this is in the body } ~Message() { delete[] buf_; } // Exception-safe copy ctor Message(const Message& orig) : bufSize_(orig.bufSize_), initBufSize_(orig.initBufSize_), msgSize_(orig.msgSize_), key_(orig.key_) { // This can throw... buf_ = new char[orig.bufSize_]; // ...so can this copy(orig.buf_, orig.buf_+msgSize_, buf_); // This can't } // Exception-safe assignment, using the copy ctor Message& operator=(const Message& rhs) { Message tmp(rhs); // Copy construct a temporary swapInternals(tmp); // Swap members with it return(*this); // When we leave, tmp is destroyed, taking // the original data with it } const char* data() { return(buf_); } private: void swapInternals(Message& msg) { // Since key_ ...