Some errors include:
(page 39)
cout << "PI = " << 3.14159 << endl;
then the output will be
PI = 3.14159Which is the same output if the function is changed to
cout << "PI = 3.14159" << endl;
although in the latter case one string literal is printed and
in the first case a string literal is printed followed by
a numeric (double) literal.
PI = 3.14159 e = 2.71828 PI*e = 8.53972(the number of decimal places after the numbers may be different on your system.)
PI*e = 3.14159 * 2.71828No multiplication is performed because the quotation marks make "3.14159*2.71828" a string literal as opposed to an arithmetic expression.
cout << "1 + 2 = 5" << endl;
is
1 + 2 = 5which shows that a computer can print things that aren't correct.
I rode the scrambler in the amusement park Hello world(this is supposed to be a pun on "hello whirled".)
(page 44)
|||||||///////// | | | o o | _| |_ |_ _| | |______| | | |
If the function Hair() is changed as shown below, a flat head is printed:
If the call Hair() is replaced by Smile(),
the output changes to the following:
(page 51)
bday2.cc: In function `int main()': bday2.cc:18: `Grace' undeclared (first use this function) bday2.cc:18: (Each undeclared identifier is reported only once bday2.cc:18: for each function it appears in.) make: *** [bday2] Error 1
To print all five verses (once for each person), then all five verses again, then all five again, rename the function main to AllVerses. Then write a new function main as shown:
(page 58)
Old MacDonald had a farm, Ee-igh, Ee-igh, oh! And on his farm he had a pig, Ee-igh, Ee-igh, oh! With a cluck cluck here And a cluck cluck there Here a cluck, there a cluck, everywhere a cluck cluck Old MacDonald had a farm, Ee-igh, Ee-igh, oh!
oldmac2.cc: In function `int main()': oldmac2.cc:41: too few arguments to function `void Verse(class string, class string)' oldmac2.cc:50: at this point in file
There is no visible output for the noise when 2 is used as the argument for parameter noise.
The call Verse("owl",2+2) will also compile.
If a standard string class is used (e.g., by using #include<string> instead of #include "CPstring.h", the compiler generates the error below (with g++) which is somewhat complicated, but shows that the conversion of 'int' to 'string' isn't allowed.
oldmac2.cc: In function `int main()': oldmac2.cc:51: conversion from `int' to non-scalar type `basic_string>' requested make: *** [oldmac2] Error 1
Old MacDonald had a farm, Ee-igh, Ee-igh, oh! And on his farm he had a baah, Ee-igh, Ee-igh, oh! With a sheep sheep here And a sheep sheep there Here a sheep, there a sheep, everywhere a sheep sheep Old MacDonald had a farm, Ee-igh, Ee-igh, oh!
If you enter "cock a doodle doo" for the noise for a rooster, only the first word will be printed as the noise since input of strings stops when the first space is encountered. You must enter "cock-a-doodle-doo" (note the hyphens) to get the entire rooster noise.
(page 94)
(page 106)
montgolfier.Ascend(50); montgolfier.Ascend(30);If the statements are reversed then the balloon will first rise to 30 meters, then will rise 20 meters more to 50 meters. The parameters to the function Ascend specify an absolute altitude, not an altitude relative to the current altitude.
Each else clause is necessary. If they're left out a grade of
100 would cause all the messages to be printed. In the code
above a grade of 75 will cause the guard (grade > 70)
to be true, and that's the only guard that will be
evaluated as true.
cout << (9 * 3 <
4 * 5) << endl;
is 0 because the expression
evaluates to 27 < 20
, which evaluates to false,
which is 0. This is because the relational operator < has
lower precedence than the arithmetic operators (see Table 4.3 on
page 120.)
The expression (9 * (3 < 4) * 5 )
evaluates
to 9 * 1 * 5
because (3 < 4)
is true which is 1. This is why 45 is output. The
parentheses are needed because < (less than); has lower
precedence than * (multiplication).
cout << 9 * 5 < 45 <<
endl
generates 0 as output because it is false and false
corresponds to 0 for output. If <= were used instead of <
then 1 would be printed since the statement would be true.
The expression (9*5 < 45 < 30)
evaluates to
45 < 45 < 30
which evaluates to 0
< 30
which is 1 (true). This depends on the
associativity of the < operator.
(page 138-139)
101.269 feet 60 minutes 1 mile ------------ * ---------- * --------- 1 minute 1 hour 5,280 feet
x
is
negative when
x >= 0
will be
false, and the call to sqrt
will NOT be made
because the whole expression must be false. This is one of the
nice things about short-circuit evaluation of boolean
expressions.
return sqrt(a*a + b*b - 2*a*b*cos(angle))
cin >> a >> b >> c
is treated like ((cin >> ) >> b) >> c
.
(page 147-149)
TensPrefix(10 * 22 / 10)
which is TensPrefix(220/10)
which is
TensPrefix(22)
because * and / have equal
precedence so in the absence of parentheses the order of
evaluation is left-to-right.
It's ok to use % here negative numbers because although the value of (-3 % 2) may not be 1 --- it's -1 on most systems --- this value is NOT zero, so it's use in the code above will work since any negative even number will yield a remainder of zero when divided by 2, even in C++.
If you want to avoid using the % (mod) operator, the code below can be used:
"yes"
or "no"
as appropriate.
Excursion Section: page 162
In this case there is no base case for the chain of recursive calls. A call of Power(3,4) to compute 3^4 will generate a recursive call Power(3,3). This generates the chain of calls
Power(3,2) Power(3,1) Power(3,0) Power(3,-1) ...and nothing (except running out of memory) will stop the chain from being extended each time another call to Power is made.
25 625 15625 390625 9765625 244140625
14 13 12 11 10 9 8 7 6 5 4 3 2 1 0The call Power(3,9) will generate the output below, again one number per line.
9 8 7 6 5 4 3 2 1 0Note that the output statement occurs before any recursive calls are made.
In general, ``optimizing'' a program with such small savings doesn't make sense until it can be determined that the savings will accrue large benefits. For example, if one billion powers were being calculated, the savings would be beneficial.
(page 184-185)
Just as a header file provides clues as to how a class can be used, but doesn't show how it's implemented, the buttons/dials on a stereo provide clues as to how to use the stereo, but not how it's put together. The header file does give away some information since the private section is visible to the user/client even though the variables cannot be accessed. A see-through stereo might be similar: users could see the circuit-boards and so on, but not access or touch them except via the dials/buttons of the stero.
NumSides()
provides access to the
value of the data. The line
will not compile (accept in the implementation file dice.cc). Instead the access functionNumSides is used.
(page 190)
(pages 203-204)
count
starts at
0 instead of 1 (and the loop test compensates for this).
Because count
is incremented before
the value of product
is updated (in contrast to
the loop in fact.cc) the value returned is correct.
divisor += 2
is changed to
divisor += 1
the function IsPrime will still
return the correct values. However, it will test many more
divisors than necessary since it will now test all numbers
between 3 and limit rather than just odd numbers. Since even
numbers have already been checked before the loop, checking
even divisors is not necessary.
IsPrime(1)
evaluates to
false (the first if statement takes care of this, checking for
numbers less than 2. This is correct, 1 is not considered
prime. The first (and only even) prime number is 2.
divisor <= limit
and
n % divisor
is false.
if (n % divisor == 0) { return false; } else { return true; }This can be shorted considerably to
return ! (n % divisor = 0);You should think about this; the expresion
n % divisor == 0
is either true or false. If it is true, then n has
a divisor so IsPrime should return false. Hence the use of !. The
expression could be written as n % divisor != 0
but
this is hard to think about (at least for me it is).
const int FEET_PER_MILE = 5280; const int OUNCES_PER_LB = 16; const double E = 2.718; const double GRAMS_PER_POUND = 453.59; const double FT_LBS_PER_ERG = 1.356e7;
(page 208-209)
num
and
count
. Since both are incremented by one each time through the
loop, one of them is superfluous. Defining and using both is ok, but
it's possible to dispense with count
and use a test of
numLines*10+ 10
so that this isn't recalculated everytime through
the loop. Smart compilers can ``optimize'' this kind of recomputation
away, however.
(page 212)
Output (one number per line):
1024 512 256 128 64 32 16 8 4 2 1 0 0 0 0 0 0 0 0 ...
(page 220)
(page 231)
(page 261)
This is the start, this is the end --- nothgin is in betweenwill indicate 7 words have been read. The words are "This", "is", "the", "start," , "this", "is", "the".
(page 280)
The statement
32,000 iterations x (32,000 words x 5.362 chars/word)/iteration == 5,490,688,000 chars x 1 second/200,000 chars = 27,453 seconds = 7.6 hours
(page 289))
The statement
Excursion (page 300)
(page 322)
position += 2*die.Roll() - 1;
since 2*die.Roll() is either 0 or 2, the right-hand-side of the expression evaluates to either -1 or +1.
Another approach might use a coin or two-sided die to determine whether the north/south OR the east/west direction would change. Another two sided die could determine up/down or left/right.
For TwoDimWalk the function TwoDimWalk:TakeStep would need to be modified to use a two-sided Dice rather than the RandGen variable (although it's possible to use RandInt instead of RandReal, but the Dice class takes care of this for you).
(Page 372)
The number of lines added is a linear function of the numer of sides on the dice being rolled. For example, for N-sided dice, the possible values are 2, 3, ..., 2N, which is (roughly) 2N different values --- the number of values is a linear function of N. The number of statements added is also a linear function of N since statements are added for initialization, update, and print, for a rough total of 3 * 2N statements which is still linear.
When using a vector as in Program 8.2 only one constant, DICE_SIDES needs to be changed to simulate 12 sided dice.
int sum = d.Roll() + d.Roll();
to
int sum = d.Roll() + d.Roll() + d.Roll();
It IS possible to create a vector of Balloon objects because the Balloon class does have a default or parameterless constructor.
(Page 379)
The parameter tracks is const in Print because it isn't changed. In Read and Shuffle the array parameter IS changed.
(Page 409)
In the first function, the largest value of k in the body is numElts - 2 which access the last array element (the one with index numElts - 1) because of a[k+1];
(Page 437)
This way the function returns a value even when its precondition isn't satisfied.
Alternatively body can be:
To write IsConsonant, just use as the function body:
It's possible to dispense with local variable 'last' and use as the if statement:
(Page 449)
and the body of the while loop can be the single statement:
or, alternatively,
Where the put member function is the 'opposite' of the get function.
Entering 1 2e7 -3 4e-9 causes the program to read the 1 into the variable intvalue. This read stops on the whitespace separating 1 from 2e7. The read/extraction into doubvalue reads all of 2e7 since this is a valid format for a double. The values are printed, and the -3 4e-9 are still left on the input stream (the parsing of 2e7 stopped on whitespace).
The next time the loop test is evaluated, the -3 is extracted into intvalue with extraction stopping because of whitespace. The 4e-9 is parsed as doubvalue.
When entering 2.5 3.7, the parse of intvalue stops at the decimal point of 2.5 because the 2 is parsed successfully, but the '.' cannot be part of an int. This leaves .5 3.7 left on the input stream. The extraction into doubvalue reads the .5, stopping at whitespace, and leaving 3.7 to be parsed the next time through the loop.
(Page 454)
In main() prompt the user for a file name and open the file:
Then modify Echo() as shown:
To avoid the global variable in the current program, pass output to Echo() each time Echo() is called (make sure to pass streams by reference).
Summary:
1:16:71 1:62:05 0:00:12 0:00:00
(Page 505)
book.tex
since there is only one file that is not also a directory in tapestry. If there is no check for a directory in files.cc then the output will be (of files.cc )
. .. chap2 chap1 chap3 book.tex library
The order of these files may be different, the file "." is the current directory, and the file ".." is the parent directory.
It's NOT necessary to use a line: entry = dir.Current() and, in fact, this won't work without the use of member functions First() and Next().
If the comparison with "." is removed, but ".." remains, then the parent directory of "mydir" will be searched recursively, which will yield "mydir" as one of the entries which will call the parent directory, and so forth and so on.
(page 521)
"Apple"then only the string Apple will be printed because the while loop test will be false since word == last as last is initialized to "Apple".
If the definition of last within the loop is removed, then entering
"Banana" "yellow" "Banana" "red" "Apple"will yield the output below:
Banana yellow Banana red Apple
(page 532)
to
It would be a good idea to use maxIndex as the identifier since now the max index is found rather than the min index.
numElts - 2 ... numElts - 1i.e., if numElts is 10 this would be the range 8..9. So the largest value that needs to be considered for k is numElts - 2.
If the test k < numElts was used the program would still work, the value of minIndex would be found without any iterations of the inner loop and the element at index minIndex = numElts - 1 would be swapped with itself. There's no reason to do this, but it doesn't make the algorithm incorrect.
The values can't be swapped because in some sense they're tied to their position within the array. To sort the vector in order of # occurrences a struct containing both the count and the character could be used. Then the location within the array isn't needed to determine the character as it is in the current program.
(Page 548)
To use the median of three, the code below can be used:
The code changes slightly if nonZeroIndex is the index of the first element AFTER the non-zero section, i.e., it is initialized to 0 rather than -1. In this case it represents both the number of non-Zero elements and the location one past the last non-Zero element. The code changes as shown below.
The variable uniqueCount is initialized to 1 since list[0] will be unique.
The variable lastWord is redundant, it could be replaced by list[uniqueCount-1] in the code below, but lastWord conveys the idea better.
It's also possible to write the for loop as below (one line shorter):
(Page 586)
The statements
This is because a has the value of 13, assigned just before the output statement, so 13 is printed first.
The value of b is set to *d of the thing pointed to by d (after b is initialized to 5). When b = *d is executed, d points to a [more precisely, the value of d is the address of the variable a] which has the value 3. This means that *d, the value of the thing pointed to by d, is 3 which is assigned to b.
The last value printed is *d, the value of the thing pointed to by d. Note d is assigned a value only once: the address of a in the statement double * d = &a;. This means that *d, the value of the thing pointed to by d, is the value of the variable a which is 13 (the first value printed).
(page 596)
Here the name of the indexing function operator [] is used.
Here's a modification that uses a vector of indexes rather than pointers in the function Sort. However, this will cause problems elsewhere in the class. For example, in the original code (two vectors of pointers) the private member function DoPrint is used to print -- it's passed either myList or myNumList since both are vectors of pointers. If myNumList is now a vector of ints, different print functions are needed to print in alphabetical order vs in order of number of occurrences.
Bottom line: the vector of indexes is probably not a good idea