1. 程式人生 > 其它 >C++ Primer(第五版) 第二章練習答案

C++ Primer(第五版) 第二章練習答案

技術標籤:C++ Primer(第五版)c++cppc語言

C++ Primer(第五版) 第二章練習答案

目錄

2.1

/**
 * 位不一樣
 * 有無負數
 * 精度不一樣
 */ 

2.2

/**
 * double double double 
 * 錢有小數
 */

2.3or2.4

#include <iostream>
#include <limits.h>

int main()
{
    unsigned u = 10, u2 = 42;

    std::cout << u2 - u << std::endl;
    std::cout << u - u2 << std::endl;

    std::cout << UINT_MAX - 32 + 1 << std::endl;

    int i = 10, i2 = 42;

    std::
cout << i2 - i << std::endl; std::cout << i - i2 << std::endl; std::cout << i - u << std::endl; std::cout << u - i << std::endl; return 0; } /** * 32 * UINT_MAX - 32 + 1 * * 32 * -32 * 0 * 0 */

2.5

#include <iostream>

int
main() { char a = 'a'; wchar_t b = L'a'; const char str[] = "a"; const wchar_t str2[] = L"a"; int i1 = 10; unsigned i2 = 10u; long i3 = 10L; unsigned long i3 = 10UL; int i4 = 012; int i5 = 0xC; double d1 = 3.14; float d2 = 3.14F; long double d3 = 3.14L; int f1 = 10; unsigned int f2 = 10u; double f3 = 10.; double f4 = 10e-2; return 0; } /** * char wchar_t const char [] const wchar_t [] * int unsigned long unsigned long int int * double float long double * int unsigned double double */

2.6

#include <iostream>

int main()
{
    int month = 9, day = 7;

    int /* month = 09, */ day = 07;

    return 0;
}

/**
 * 十進位制和八進位制
 * 八進位制 0-7 沒有 9
 *

2.7

#include <iostream>

int main()
{
    std::cout << "Who goes with F\145rgus?\012";

    auto i1 = 3.14e1L;
    // float i2 = 1024f;
    auto i3 = 3.14L;

    return 0;
}


/**
 * \145 = e, \012 = \n
 * 
 * long double  float(沒有小數點,錯誤)  long double
 */

2.8

#include <iostream>

int main()
{
    std::cout << "2\tM\n";

    return 0;
}

2.9

#include <iostream>

int main()
{
    // a
    int input_value = 0;
    std::cin >> input_value;

    // b
    double i = {3.14};

    // c
    double salary = 9999.99, wage = salary;

    // d
    double i = 3.14;

    return 0;
}

2.10

#include <iostream>
#include <string>

std::string global_str;
int global_int;

int main()
{
    int local_int;
    std::string local_str;

    std::cout << global_str << std::endl;
    std::cout << global_int << std::endl;
    std::cout << local_int << std::endl;
    std::cout << local_str << std::endl;

    return 0;
}

/**
 * string類建構函式初始化的空字串
 * 全域性變數自動初始化為0
 * 區域性變數未定義
 * string類建構函式初始化的空字串
 */

2.11

#include <iostream>

extern int ix = 1024;
int iy;  
extern int iz;

/**
 * 警告: ix已初始化並宣告為extern
 * 宣告並定義
 * 宣告
 */

int main()
{

    return 0;
}

2.12

/**
 * double    關鍵字
 * catch-22  中橫線
 * 1_or_2    數字開頭
 */

2.13

#include <iostream>

int i = 42;

int main()
{
    int i = 100;
    int j = i;

    printf("%d\n", j);

    return 0;
}

2.14

#include <iostream>

int main()
{
    int i = 100, sum = 0;
    for (int i = 0; i != 10; ++i)
        sum += i;

    std::cout << i << " " << sum << std::endl;

    return 0;
}


/**
 * 100 45
 */

2.15

/**
 * (b)  int &rval1 = 1.01;  非常量引用的初始值必須為左值 
 * 
 * (d)  int &rval3;  宣告為引用但未初始化
 */

2.16

#include <iostream>

int main()
{
    int i = 0, &r1 = i;
    double d = 0, &r2 = d;

    r2 = 3.14159;
    r2 = r1;
    i = r2;
    r1 = d;

    return 0;
}

/**
 * 全部合法
 */

2.17

#include <iostream>

int main()
{
    int i, &ri = i;
    i = 5;
    ri = 10;

    std::cout << i << " " << ri << std::endl;

    return 0;
}

/**
 * 10 10
 */

2.18

#include <cstdio>

int main()
{
    int *pi = nullptr, a = 10;

    pi = &a;
    printf("%d\n", *pi);
    printf("%d\n", a);

    *pi = 20;
    printf("%d\n", *pi);
    printf("%d\n", a);


    return 0;
}

2.19

/**
 * 指標是物件,引用不是
 */

2.20

#include <iostream>

int main()
{
    int i = 42;
    int *p1 = &i;
    *p1 = *p1 * *p1;

    std::cout << *p1 << std::endl;

    return 0;
}

/**
 * 定義 i = 42, 
 * p1 指向 i,
 * *p1 = 42 * 42
 */

2.21

int main()
{
    int i = 0;

    // 指標型別不匹配
    double *dp = &i;
    // 指標型別不匹配
    int *ip = i;

    int *p = &i;

    return 0;
}

2.22

int main() 
{
    int *p = nullptr;

    // 指標 != nullptr 為 true
    if (p) { }
    // 指向物件 != 0 為 true
    if (*p) { }

    return 0;
}

2.23

/**
 * 不能 因為即使指向非法物件,有時候也能正常得到結果
 */

2.24

int main()
{
    int i = 42;
    // void* 指向任何型別地址
    void *p = &i;
    // 型別不匹配
    long *lp = &i;

    return 0;
}

2.25

#include <iostream>

int main()
{
#if 0
    int i = 42;
    int *p;
    int *&r = p;

    r = &i;
    printf("%d\n", *r);    
    printf("%d\n", *p);    

    printf("%p\n", r);    
    printf("%p\n", p);    
    printf("%p\n", &i);    
#endif
    // 指向int的指標  int  引用繫結 i
    int *ip, i, &r = i;

    // int  指標指向空
    int i, *ip = 0;

    // 指標  int
    int *ip, ip2;

    return 0;
}

2.26

#include <iostream>

int main()
{
    // 沒初始化
    const int buf;

    int cnt = 0;
    const int sz = cnt;

    // const 限定
    ++cnt; ++sz;

    return 0;
}

2.27

#include <iostream>

int main()
{
    // 非常量引用的初始值必須為左值
    // int i = -1, &r = 0;

    // const int i2 = 10;
    // const int i2, 則不合法
    // int *const p2 = &i2;

    // 合法
    // const int i = -1, &r = 0;

    // 合法
    // const int *const p3 = &i2;

    // 合法
    // const int *p1 = &i2;

    // 引用要初始值
    // const int &const r2;

    // 合法
    // const int i2 = i, &r = i;

    return 0;
}

2.28

#include <iostream>

int main()
{
    // 常量 變數 "cp" 需要初始值設定項
    int i, *const cp;
    // 常量 變數 "p2" 需要初始值設定項
    int *p1, *const p2;
    // 常量 變數 "ic" 需要初始值設定項
    const int ic, &r = ic;
    // 常量 變數 "p3" 需要初始值設定項
    const int *const p3;
    // 不是常量指標不需要初始值 合法
    const int *p;

    return 0;
}

2.29

#include <iostream>

int main()
{
    // 常量 變數 "cp" 需要初始值設定項
    int i, *const cp;
    // 常量 變數 "p2" 需要初始值設定項
    int *p1, *const p2;
    // 常量 變數 "ic" 需要初始值設定項
    const int ic, &r = ic;
    // 常量 變數 "p3" 需要初始值設定項
    const int *const p3;
    // 不是常量指標不需要初始值 合法
    const int *p;

    // 合法 常量賦值給變數
    i = ic;
    // 不能將 "const int *" 型別的值分配到 "int *" 型別的實體 
    p1 = p3;
    // 不能將 "const int *" 型別的值分配到 "int *" 型別的實體
    p1 = &ic;
    // p3 常量指標
    p3 = &ic;
    // p2 常量指標
    p2 = p1;
    // const限定
    ic = *p3;

    return 0;
}

2.30

#include <iostream>

int main()
{
    int i = 0;

    // 頂層const
    const int v2 = 0;
    int v1 = v2;
    int *p1 = &v1, &r1 = v1;
    // 底層const      指向常量的常量指標    底層const
    const int *p2 = &v2, *const p3 = &i, &r2 = v2;

    return 0;
}

2.31

#include <iostream>

int main()
{
    int i = 0;

    // 頂層const
    const int v2 = 0;
    int v1 = v2;
    int *p1 = &v1, &r1 = v1;
    // 底層const      指向常量的常量指標    底層const
    const int *p2 = &v2, *const p3 = &i, &r2 = v2;

    // 合法 常量賦值給變數
    r1 = v2;
    // 不能將 "const int *" 型別的值分配到 "int *" 型別的實體
    p1 = p2; p2 = p1;
    // 不能將 "const int *" 型別的值分配到 "int *" 型別的實體
    p1 = p3; p2 = p3;

    return 0;
}

2.32

#include <iostream>

int main()
{
    int null = 0, *p = null;
    
    int null = 0, *p = nullptr;

    return 0;
}

2.33or34

#include <iostream>

int main()
{
    int i = 10;
    // 頂層             底層
    const int ci = i, &cr = ci;


    auto a = i;

    auto b = ci;
    auto c = cr;
    auto d = &i;
    auto e = &ci;

    const auto f = ci;

    auto &g = ci;
    // auto &h = 42;
    const auto &j = 42;

    auto k = ci, &l = i;
    auto &m = ci, *p = &ci;

    // auto &n = i, *p2 = &ci;

    std::cout << a << std::endl;
    std::cout << b << std::endl;
    std::cout << c << std::endl;

    a = 42;  // int 正確
    b = 42;  // int 正確
    c = 42;  // int 正確
    // d = 42;  // int * 指標
    // e = 42;  // const int * 指向常量的指標
    // g = 42;  // const int & 不能修改


    std::cout << a << std::endl;
    std::cout << b << std::endl;
    std::cout << c << std::endl;


    return 0;
}

2.35

#include <iostream>

int main()
{
    // 頂層const
    const int i = 42;
    // int (忽略頂層const, 保留底層const)
    auto j = i; 
    // 常量引用 (可以不用加const)
    const auto &k = i;  /* auto &k = i; */
    // 對常量取地址是底層const
    auto *p = &i;
    // (cosnt) int       const int &
    const auto j2 = i, &k2 = i;

    return 0;
}

2.36

#include <iostream>

int main()
{   
    int a = 3, b = 4;
    // int
    decltype(a) c = a;
    // int &
    decltype((b)) d = a;
    ++c;
    ++d;
    // 4 4 4 4
    std::cout << &a << std::endl;
    std::cout << &b << std::endl;
    std::cout << &c << std::endl;
    std::cout << &d << std::endl;
    
    printf("%p\n", &a);
    printf("%p\n", &b);
    printf("%p\n", &c);
    printf("%p\n", &d);

    return 0;
}

2.37

#include <iostream>

int main()
{
    int a = 3, b = 4;
    // int 3
    decltype(a) c = a;
    // int & 3  (不執行賦值)
    decltype(a = b) d = a;

    printf("%d %d %d %d\n", a, b, c, d);

    return 0;
}

2.38

#include <iostream>

int main()
{
    /**
     * decltype 保留頂層const和引用
     * auto 丟棄頂層const和引用
     */

    const int a = 10, &b = a;

    // int
    auto c1 = a;
    // const int
    decltype(a) c2 = a;

    // int
    auto d1 = b;
    // const int &
    decltype(b) d2 = b;

    return 0;
}

2.39

#include <iostream>

struct Foo { }

int main()
{


    return 0;
}

/**
 * [2_39.cpp 2021-02-17 09:53:32.462]
,,2_39.cpp:3:15: error: expected ';' after struct definition
 struct Foo { }
               ^
               ;
*/

2.40

#ifndef SALES_DATA
#define SALES_DATA

#include <iostream>
#include <string>


struct Sales_data {
    // 書號
    std::string bookNo;
    // 售賣單位
    unsigned units_sold = 0;
    // 收入
    double revenue = 0.0;
};

#endif

2.41or42

#include "2_40.h"
#include <iostream>
#include <vector>
#include <map>
#include <utility>

#if 0
/**
 * 1_20練習
 */
int main()
{
    std::vector<Sales_data> data;
    Sales_data temp;

    // 輸入書名
    while (std::cin >> temp.bookNo)
    {
        // 輸入售賣單位 和 收入
        std::cin >> temp.units_sold;
        std::cin >> temp.revenue;

        data.push_back(temp);
    }

    for (auto &i : data)
    {
        std::cout << i.bookNo << ", "
                  << i.units_sold << ", "
                  << i.revenue << std::endl;
    }

    return 0;
#elif 0
/**
 * 1.21練習
 */
int main()
{
    Sales_data data1, data2;

    while (true)
    {
        std::cin >> data1.bookNo >> data1.units_sold >> data1.revenue;
        std::cin >> data2.bookNo >> data2.units_sold >> data2.revenue;

        if (data1.bookNo == data2.bookNo)
        {
            std::cout << data1.bookNo << ", "
                      << data1.units_sold + data2.units_sold << ", "
                      << data1.revenue + data2.revenue << std::endl;
            break;
        }
        else
        {
            std::cerr << "Re enter" << std::endl;
        }
    }



    return 0;
}
#elif 0
/**
 * 1_22練習
 */
int main()
{
    std::map<std::string, Sales_data> datas;
    Sales_data temp;

    // 輸入
    while (std::cin >> temp.bookNo >> temp.units_sold >> temp.revenue)
    {
        // 沒找到即不在 map 中
        if (datas.find(temp.bookNo) == datas.end())
        {
            // 插入
            datas.insert(std::pair<std::string, Sales_data>(temp.bookNo, temp));
        }
        else // 計算總和
        {
            datas[temp.bookNo].units_sold += temp.units_sold;
            datas[temp.bookNo].revenue += temp.revenue;
        }
    }

    for (const auto &i : datas)
        std::cout << i.first << ": "
                  << i.second.units_sold << " "
                  << i.second.revenue << std::endl;

    return 0;
}
#elif 0
/**
 * 1_23
 */
int main()
{
    std::map<std::string, size_t> datas;
    Sales_data temp;

    // 輸入
    while (std::cin >> temp.bookNo >> temp.units_sold >> temp.revenue)
        // 同一本書加一
        ++datas[temp.bookNo];

    for (const auto &i : datas)
        std::cout << i.first << " : "
                  << i.second << std::endl;

    return 0;
}
#elif 0
/**
 * 1_24
 */
int main()
{
    std::map<std::string, std::vector<Sales_data>> datas;
    Sales_data temp;

    // 輸入
    while (std::cin >> temp.bookNo >> temp.units_sold >> temp.revenue)
    {
        // 不在 map 中
        if (datas.find(temp.bookNo) == datas.end())
        {
            // 插入
            datas.insert(std::pair<std::string, std::vector<Sales_data>>(temp.bookNo, std::vector<Sales_data>()));
            datas[temp.bookNo].push_back(temp);
        }
        else
        {
            datas[temp.bookNo].push_back(temp);
        }
    }

    for (auto &i : datas)
    {
        std::cout << i.first << " -> "
                  << i.second.size() << std::endl;
        for (auto &j : i.second)
            std::cout << j.bookNo << " "
                      << j.units_sold << " "
                      << j.revenue << std::endl;
    }

    return 0;
}
#elif 1
/**
 * 1_25
 */
int main()
{
    Sales_data total;

    // 輸入
    if (std::cin >> total.bookNo >> total.units_sold >> total.revenue)
    {
        Sales_data trans;
        // 輸入
        while (std::cin >> trans.bookNo >> trans.units_sold >> trans.revenue)
        {
            // 判斷書名是否相同
            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 << 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 << std::endl;

    }
    else // 輸入失敗
    {
        std::cerr << "No data?!" << std::endl;
        return -1;
    }

    return 0;
}

#endif