[ fromfile: errata.xml id: errata ]
This document was last updated on $Date: 2009-06-08 16:01:21 -0400 (Mon, 08 Jun 2009) $.
p.6. “C with Objects”: s/Objects/Classes
p.8, add an item to the numbered list:
3. It is installed by your package manager as qmake-qt4,
to avoid conflict with Qt3 packages.
p.22 Table 1.2 should be replaced with:
Table F.1. Simple Types Hierarchy
| byte/char types | integral types | floating point types |
|---|---|---|
| bool | short int | float |
| char | unsigned short | double |
| signed char | int | long double |
| unsigned char | unsigned int | |
| wchar_t | anyType* | |
| long int | ||
| unsigned long |
p.29 exercise #2: For windows portability, s/random()/rand()/. random() is only POSIX compliant, while rand() is from C standard library.
p.33, Example 1.16, some #include directives should have been included at the top of the listing:
#include <iostream> #include <sstream> #include <fstream>
P.58, The constructor at the top of the page should be:
Complex::Complex(double realPart) :
m_R(realPart), m_I(0) {
}
P.58, Section 2.8 Subobjects should be the last section of Chapter 2 (i.e., after the section, const Member Functions.
P.72, diagram for Problem 3 should be this:

p.83, There should be no semicolon at the end of the code example, main.cpp.
p.83, the qapp.pro is missing a line:
CONFIG += console
P.83, just before the start of section 3.2:
The last line, CONFIG += console, only necessary on Windows platforms, tells the compiler to build a “console” application, which can interact with the user via standard input/output streams.
Page 101, first para: s/Employers many hire many/Employers may hire many/
Page 101, Relationships exercises, some clarification of wording:
Implement an Employer::findJobs() function to return a list of all open Positions.
Implement a Person::apply(Position*) function to call Employer::hire(), and return the same result as hire, if successful.
For the Person methods which return information about employment, be sure to handle the case where the Person is not employed yet, and return something meaningful.
P.121, Example 5.14 needs one member function to be corrected so that it reads:
void setNameR( QString& newName) {
newName += " Dobbs"; /* changes the original QString */
m_Name = newName;
}
Page 137, UML diagram should be this:
Page 138 and 143, In the Student class definition:
The third parameter of the constructor should be named major - (not m_Major).
The member function yearStr() should be declared static.
Page 157, Example 6.22: use member init lists in constructors:
Account::Account(unsigned acctNum, double balance, string owner) :
m_AcctNum(acctNum), m_Balance(balance), m_Owner(owner)
{ }
JointAccount::JointAccount (unsigned acctNum, double balance,
string owner, string jowner)
:Account(acctNum, balance, owner),
m_JointOwner(jowner) /* base class initialization required */
{ }
JointAccount::JointAccount (const Account& acc, string jowner)
:Account(acc), /* compiler-generated copy constructor call */
m_JointOwner(jowner)
{ }
Page 172, section on Installing Libraries, add a note:
| Building DLLs | |
|---|---|
There is a thread on the subject at qtcentre.org, which should save you a lot of time when you build your first DLL. |
Page 183, example 18.1 - some changes to the code:
QString dirname = finfo.fileName(); if ((dirname==".") || (dirname == "..")) return; QDir sd(finfo.filePath()); if (skipDir(sd)) continue; recurseAddDir(sd); } else { if (finfo.extension(false)=="mp3") { addMp3File(finfo.absFilePath()); /* non-reusable part */ } }
Some changes to FileVisitor class definition:
Example F.1. src/libs/utils/filevisitor.h
[ . . . . ] #include <QDir> #include <QObject> #include <QStringList> #include "utils_export.h" class UTILS_EXPORT FileVisitor : public QObject { Q_OBJECT public: FileVisitor(QString nameFilter="*", bool recursive=true, bool symlinks=false); FileVisitor(QStringList nameFilterList, bool recursive=true, bool symlinks = false); public slots: void processFileList(QStringList sl); void processEntry(QString pathname); signals: void foundFile(QString filename); protected: virtual void processFile(QString filename);[ . . . . ] protected: QStringList m_filterList; bool m_Recursive; QDir::Filters m_DirFilter; }; [ . . . . ]
FileVisitor::processDir() has been updated:
Page 187 CodeVisitor class definition has been improved:
Example F.3. src/visitor/codevisitor/codevisitor.h
[ . . . . ]
class CodeVisitor : public FileVisitor {
public:
CodeVisitor(QString filter = "*.h,*.cpp", bool recursive = true);
CodeVisitor(QStringList filterList, bool recursive = true);
void processFile(QString filename);
int getNumFiles() const;
QString getResultString() const;
private:
int m_NumFiles;
QStringList m_Result;
};
[ . . . . ]
Page 188, Example 8.6, codevisitor-test.cpp has been improved:
Example F.4. src/visitor/codevisitor/codevisitor-test.cpp
#include <argumentlist.h> #include <codevisitor.h> #include <QApplication> #include <QTextStream> #include <stdlib.h> static QTextStream cerr(stderr); void usage(QString appname) { cerr << appname << " Usage: \n" << "codevisitor [?] [-r] [-d startdir] [-f filter] [file-list]\n" << "\t-? \tthis help list\n" << "\t-r \tvisitor will recurse into subdirs\n" << "\t-d startdir\tspecifies starting directory\n" << "\t-f filter\tfilename filter to restrict visits (i.e. -f \"*.cpp\") \n" << "\toptional list of files to be visited\n" << "Use double quotes to delimit all strings in command line."<< endl; } int main(int argc, char** argv) { ArgumentList al(argc, argv); QString appname = al.takeFirst();if (al.getSwitch("?") or al.getSwitch("-?")) { usage(appname); exit(1); } bool recursive(al.getSwitch("-r")); QString startdir(al.getSwitchArg("-d")); QStringList filterList; QString filter; while ((filter = al.getSwitchArg("-f", QString())) != QString()) { cerr << "added filter: " << filter << endl; filterList << filter; } CodeVisitor cvis(filterList, recursive); if (startdir != QString()) { // change directory to startdir cvis.processEntry(startdir); } if (al.size()) { cvis.processFileList(al); } cerr << "Files Processed: " << cvis.getNumFiles() << endl; cerr << cvis.getResultString() << endl; return 0; }
Page 190, Question 2, “Why Does the FileVisitor need to be Recursive?“ The answer is: It does not need to be. A better question here would be: “How would you rewrite the FileVisitor to not be recursive?“
Page 204, member variable in Examples 9.7 renamed:
QErrorMessage* message; should be
QErrorMessage* m_Message; This change produces changes in two lines of Example 9.8:
Messager::Messager(QString msg, QWidget* parent) : m_Parent(parent) { m_Message = new QErrorMessage(parent); setObjectName(msg); } void Messager::shout() { m_Message->showMessage(objectName()); }
Page 205, magic numbers -273 and 360 in Example 9.9 should be const int.
Page 223, the diagram for the cardgame exercise should be replaced with this one:

Page 228, Figure 10.3 - ContactListWriter has a duplicated function declaration.
Page 228, remove the word “insertion” from the partial sentence, “We achieve this by defining the following insertion operators:“
Page 287, Example 12.11 should be this:
Example F.5. src/qonsole/keyevents/qonsole.cpp
[ . . . . ]
void Qonsole::updateCursor() {
QTextCursor cur = m_Logw->textCursor();
cur.movePosition(QTextCursor::End, QTextCursor::KeepAnchor);
m_Logw->setTextCursor(cur);
}
void Qonsole::execute() {
QByteArray bytes = m_UserInput.toUtf8();
m_Bash->write(bytes);
m_UserInput = "";
}
Page 315, Example 13.4, there are mistakes in nlformat and nlformat2 regular expressions.
QRegExp nlformat ("(\\+|00)?[\\s-]?(31)[\\s-]?(\\d\\d)[\\s-]?(.*)$"); QRegExp nlformat2 ("(\\d\\d)(\\d\\d)(\\d{3})");
Page 512, array example should be this:
int a[] = {10, 11, 12, 13, 14, 15};
void f(int a[]) {
[ ... ]
}
[ ... ]
f(a);
Page 596, small typo:
s/unable/enable
p. 601 [qttestlib]
s/Harris/Hards
| Generated: $Date: 2009-09-08 12:15:32 -0400 (Tue, 08 Sep 2009) $ | © 2009 Alan Ezust and Paul Ezust. |