C++Primer fifth edition exercise answers [Chapter 2]

C++Primer Fifth Edition Exercise Answers [General List]: https://blog.csdn.net/Dust_Evc/article/details/114334124

2.1

C++ stipulates that `short` and `int` must be at least 16 bits, `long` must be at least 32 bits, and `long long` must be at least 64 bits.
Signed types can represent positive, negative, and 0, while unsigned types can only represent 0 and positive integers.

Usage:
1. Generally, `int` is used for integer arithmetic, and `short` is rarely used in practice because it is too small. `long` usually has the same size as `int`. If the data is very large, you can use `long long`.
2. If you confirm that the data is non-negative, then use the `unsigned` unsigned type.
3. Use `double` when performing floating-point operations, because `float` usually has insufficient precision and the calculation cost of double-precision floating-point numbers and single-precision floating-point numbers is almost the same.

2.2

Use `double` or `float`.

2.3

unsigned u = 10, u2 = 42;
std::cout << u2 - u << std::endl;    //32
std::cout << u - u2 << std::endl;    //4294967264
int i = 10, i2 = 42;
std::cout << i2 - i << std::endl;    //32
std::cout << i - i2 << std::endl;    //-32
std::cout << i - u << std::endl;    //0
std::cout << u - i << std::endl;    //0

2.4

#include <iostream>

int main()
{
	unsigned u = 10, u2 = 42;
	std::cout << u2 - u << std::endl;   // 32
	std::cout << u - u2 << std::endl;   // 4294967264
	int i = 10, i2 = 42;
	std::cout << i2 - i << std::endl;   // 32
	std::cout << i - i2 << std::endl;   // -32
	std::cout << i - u << std::endl;    // 0
	std::cout << u - i << std::endl;    // 0

	return 0;
}

2.5

(a): Character literal, wide character literal, character string literal, wide character string literal

(b): Decimal integer, decimal unsigned integer, decimal long integer, octal integer, hexadecimal integer

(c): double, float, long double

(d): Decimal integer, decimal unsigned integer, double, double

2.6

The first line defines the decimal integer.
The second line defines an octal integer, but the month variable is invalid because there is no 9 in octal.

2.7

(a): Who goes with Fergus? (line feed), string type

(b): long double

(c): Invalid, because the suffix f can only be used for floating-point literals, and 1024 is an integer.

(d): long double

2.8

int main()
{
    std::cout << 2 << "\115\012";
    std::cout << 2 << "\t\115\012";
    return 0;
}

2.9

(a): 应该先定义再使用。

int input_value = 0;
std::cin >> input_value;


(b): 用列表初始化内置类型的变量时,如果存在丢失信息的风险,则编译器将报错。

double i = { 3.14 };


(c): 在这里 wage 是未定义的,应该在此之前将其定义。

double wage;
double salary = wage = 9999.99;


(d): 不报错,但是小数部分会被截断。

double i = 3.14;

2.10

`global_str` and `global_int` are global variables, so the initial value is an empty string and 0 respectively.
`local_int` is a local variable and is not initialized. Its initial value is undefined.
`local_str` is an object of string class. Its value is determined by the class and is an empty string. 

2.11

(a): Definition
(b): Definition
(c): Declaration

2.12

`(a)`, `(c)`, `(d)` are illegal.

2.13

The value of `j` is `100`, and the local variable `i` covers the global variable `i`.

2.14

legitimate. The output is `100 45`.

2.15

`(b)` and `(d)` are illegal, `(b)` reference must be bound to the object, `(d)` reference must be initialized.

2.16

(a): Legal. Assign a value of 3.14159 to d.
(b): Legal. Automatic conversion (int->double) will be performed.
(c): Legal. Decimal interception will occur.
(d): Legal. Decimal interception will occur.

2.17

10, 10

2.18

int a = 0, b = 1;
int *p1 = &a, *p2 = p1;

// change the value of a pointer.
p1 = &b;
// change the value to which the pointer points
*p2 = b;

2.19

1. The reference is an alias for another object, and the pointer itself is an object.
2. The reference must be initialized, and once the reference is defined, it can no longer be bound to other objects. The pointer does not need to be assigned an initial value when it is defined, and it can also be re-assigned to point to other objects.

2.20

Let the pointer `pi` point to `i`, and then re-assign the value of `i` to 42 * 42 (1764).

2.21

(a): Illegal. You cannot point a pointer to `double` to `int`.
(b): Illegal. You cannot assign an `int` variable to a pointer.
(c): Legal.

2.22

`if (p) // ...` judge whether p is a null pointer, 
`if (*p) // ...` judge whether the value of the object pointed to by p is 0

2.23

No, because we must first determine whether the pointer is legal before judging whether the object it points to is legal.

2.24

`void *` is inherited from the C language and can point to any type of object. The other pointer types must strictly match the pointed object.

2.25

(a): ip is a pointer to int, i is an int, and r is a reference to i.
(b): i is int, ip is a null pointer.
(c): ip is a pointer to int, ip2 is an int.

2.26

const int buf; // illegal, const object must be initialized
int cnt = 0; // legal
const int sz = cnt; // legal
++cnt; ++sz; // illegal, const object cannot be changed

2.27

int i = -1, &r = 0; // illegal, r must refer to an object
int *const p2 = &i2; // legal
const int i = -1, &r = 0; // legal
const int *const p3 = &i2; // legal
const int *p1 = &i2; // legal
const int &const r2; // illegal, r2 is a reference, the reference has no top-level const
const int i2 = i, &r = i; // legal

2.28

int i, *const cp; // illegal, const pointer must be initialized
int *p1, *const p2; // illegal, const pointer must be initialized
const int ic, &r = ic; // illegal, const int must be initialized
const int *const p3; // illegal, const pointer must be initialized
const int *p; // legal. A pointer to const int

2.29

i = ic; // legal, constant assignment to ordinary variable
p1 = p3; // illegal, p3 is const pointer and cannot be assigned to ordinary pointer
p1 = ⁣ // illegal, ordinary pointer cannot point to constant
p3 = ⁣ / / Legal, p3 is a constant pointer and points to a constant
p2 = p1; // Legal, you can assign an ordinary pointer to a constant pointer
ic = *p3; // Legal, after the value of p3 is an int and then assigned to ic

2.30

const int v2 = 0; int v1 = v2;
int *p1 = &v1, &r1 = v1;
const int *p2 = &v2, *const p3 = &i, &r2 = v2;

2.31

r1 = v2; // legal, the top const is not affected when copying
p1 = p2; // illegal, p2 is the bottom const, if you want to copy, you must require p1 to be the bottom const
p2 = p1; // legal, int* can Converted to const int*
p1 = p3; // illegal, p3 is a low-level const, p1 is not
p2 = p3; // legal, p2 and p3 are both low-level const, the top const is ignored when copying

2.32

legitimate. The pointer can be initialized to 0 to indicate a null pointer.

2.33

a=42; // a is an int
b=42; // b is an int, (the top const of ci is ignored when copying)
c=42; // c is also an int
d=42; // d It is an int *, so the statement is illegal
e=42; // e is a const int *, so the statement is illegal
g=42; // g is a reference to a const int, and the references are all underlying const, so they cannot be assigned

2.34

#include <iostream>

int main()
{
	int i = 0, &r = i;
	auto a = r;   // a是一个整数(r是i的别名,而i是以一个整数)

	const int ci = i, &cr = ci;
	auto b = ci; // b是一个整数(ci的顶层const特性被忽略掉了)
	auto c = cr; // c是一个整数(cr是ci的别名,ci本身是一个顶层const)
	auto d = &i; // d是一个整型指针(整数的地址就是指向整数的指针)
	auto e = &ci; // e是一个指向整数常量的指针(对常量对象去地址是一种底层const)

	const auto f = ci; // ci的推演类型是int,f是const int
	auto &g = ci; // g是一个整型常量引用,绑定到ci

	std::cout << a << std::endl;
	std::cout << b << std::endl;
	std::cout << c << std::endl;
	std::cout << d << std::endl;
	std::cout << e << std::endl;
	std::cout << f << std::endl;
	std::cout << g << std::endl;
	std::cout << "--------------" << std::endl;
	a = 42; b = 42; c = 42; //d = 42; e = 42; g = 42;

	std::cout << a << std::endl;
	std::cout << b << std::endl;
	std::cout << c << std::endl;
	std::cout << d << std::endl;
	std::cout << e << std::endl;
	std::cout << f << std::endl;
	std::cout << g << std::endl;

	return 0;
}

2.35

j is int, k is a reference to const int, p is const int *, j2 is const int, and k2 is a reference to const int.

2.36

c is of type int with a value of 4. d is of type int &, bound to a, the value of a is 4.

2.37

c is of type int with a value of 3. d is of type int& and is bound to a.

2.38

decltype handles top-level const and references differently from auto, decltype keeps top-level const and references.

int i = 0, &r = i;
//相同
auto a = i;
decltype(i) b = i;

//不同 d 是一个 int&
auto c = r;
decltype(r) d = r;

2.39

You are prompted to enter a semicolon.

2.40

struct Sale_data
{
    std::string bookNo;
    std::string bookName;
    unsigned units_sold = 0;
    double revenue = 0.0;
    double price = 0.0;
    //...
}

2.41

1.5.1

#include <iostream>
#include <string>

struct Sale_data
{
    std::string bookNo;
    unsigned units_sold = 0;
    double revenue = 0.0;
};

int main()
{
    Sale_data book;
    double price;
    std::cin >> book.bookNo >> book.units_sold >> price;
    book.revenue = book.units_sold * price;
    std::cout << book.bookNo << " " << book.units_sold << " " << book.revenue << " " << price;

    return 0;
}

1.5.2

#include <iostream>
#include <string>

struct Sale_data
{
    std::string bookNo;
    unsigned units_sold = 0;
    double revenue = 0.0;
};

int main()
{
    Sale_data book1, book2;
    double price1, price2;
    std::cin >> book1.bookNo >> book1.units_sold >> price1;
    std::cin >> book2.bookNo >> book2.units_sold >> price2;
    book1.revenue = book1.units_sold * price1;
    book2.revenue = book2.units_sold * price2;

    if (book1.bookNo == book2.bookNo)
    {
        unsigned totalCnt = book1.units_sold + book2.units_sold;
        double totalRevenue = book1.revenue + book2.revenue;
        std::cout << book1.bookNo << " " << totalCnt << " " << totalRevenue << " ";
        if (totalCnt != 0)
            std::cout << totalRevenue / totalCnt << std::endl;
        else
            std::cout << "(no sales)" << std::endl;
        return 0;
    }
    else
    {
        std::cerr << "Data must refer to same ISBN" << std::endl;
        return -1;  // indicate failure
    }
}

1.6

#include <iostream>
#include <string>

struct Sale_data
{
    std::string bookNo;
    unsigned units_sold = 0;
    double revenue = 0.0;
};

int main()
{
    Sale_data total;
    double totalPrice;
    if (std::cin >> total.bookNo >> total.units_sold >> totalPrice)
    {
        total.revenue = total.units_sold * totalPrice;

        Sale_data trans;
        double transPrice;
        while (std::cin >> trans.bookNo >> trans.units_sold >> transPrice)
        {
            trans.revenue = trans.units_sold * transPrice;

            if (total.bookNo == trans.bookNo)
            {
                total.units_sold += trans.units_sold;
                total.revenue += trans.revenue;
            }
            else
            {
                std::cout << total.bookNo << " " << total.units_sold << " " << total.revenue << " ";
                if (total.units_sold != 0)
                    std::cout << total.revenue / total.units_sold << std::endl;
                else
                    std::cout << "(no sales)" << std::endl;

                total.bookNo = trans.bookNo;
                total.units_sold = trans.units_sold;
                total.revenue = trans.revenue;
            }
        }

        std::cout << total.bookNo << " " << total.units_sold << " " << total.revenue << " ";
        if (total.units_sold != 0)
            std::cout << total.revenue / total.units_sold << std::endl;
        else
            std::cout << "(no sales)" << std::endl;

        return 0;
    }
    else
    {
        std::cerr << "No data?!" << std::endl;
        return -1;  // indicate failure
    }
}

2.42

Sale_data.h

struct Sale_data
{
    std::string bookNo;
    std::string bookName;
    unsigned units_sold = 0;
    double revenue = 0.0;
    double price = 0.0;
}

1.5.1

#include <iostream>
#include "Sale_data.h"

int main()
{
	Sales_data book;
	double price;
	std::cin >> book.bookNo >> book.units_sold >> price;
	book.CalcRevenue(price);
	book.Print();

	return 0;
}

1.5.2

#include <iostream>
#include "Sale_data.h"

int main()
{
	Sales_data book1, book2;
	double price1, price2;
	std::cin >> book1.bookNo >> book1.units_sold >> price1;
	std::cin >> book2.bookNo >> book2.units_sold >> price2;
	book1.CalcRevenue(price1);
	book2.CalcRevenue(price2);

	if (book1.bookNo == book2.bookNo)
	{
		book1.AddData(book2);
		book1.Print();
		return 0;
	}
	else
	{
		std::cerr << "Data must refer to same ISBN" << std::endl;
		return -1;  
	}
}

1.6

#include <iostream>
#include "Sale_data.h"

int main()
{
	Sales_data total;
	double totalPrice;
	if (std::cin >> total.bookNo >> total.units_sold >> totalPrice)
	{
		total.CalcRevenue(totalPrice);
		Sales_data trans;
		double transPrice;
		while (std::cin >> trans.bookNo >> trans.units_sold >> transPrice)
		{
			trans.CalcRevenue(transPrice);
			if (total.bookNo == trans.bookNo)
			{
				total.AddData(trans);
			}
			else
			{
				total.Print();
				total.SetData(trans);
			}
		}
		total.Print();
		return 0;
	}
	else
	{
		std::cerr << "No data?!" << std::endl;
		return -1;  
	}
}

 

Guess you like

Origin blog.csdn.net/Dust_Evc/article/details/114385319