《C++ Primer Plus》(第6版)第7章编程练习

《C++ Primer Plus》(第6版)第7章编程练习

1. 调和平均数

编写一个程序,不断要求用户输入两个数,直到其中的一个为0。对于每两个数,程序将使用一个函数来计算它们的调和平均数,并将结果返回给main(),而后者将报告结果。调和平均数指的是倒数平均值的倒数,计算公式如下:
调和平均数=2.0 * x * y / (x+ y)

代码:

#include <iostream>
using namespace std;

double cal_harmonic_mean(double, double);

int main()
{
    int a, b;

    cout << "Enter two numbers, I will calculate their harmonic average.\n";
    while (1)
    {
        cout << "a:";
        cin >> a;
        cout << "b:";
        cin >> b;
        if (!a | !b)
            break;
        cout << "The harmonic mean of a and b is " << cal_harmonic_mean(a, b) << ".\n";
    }
    cout << "Done!\n";

    system("pause");
    return 0;
}
double cal_harmonic_mean(double x, double y)
{
    return 2.0 * x * y / (x + y);
}

运行结果:

在这里插入图片描述

2. 高尔夫成绩

编写一个程序,要求用户输入最多10个高尔夫成绩,并将其存储在一个数组中。程序允许用户提早结束输入,并在一行上显示所有成绩,然后报告平均成绩。请使用3个数组处理函数来分别进行输入、显示和计算平均成绩。

代码:

#include <iostream>
using namespace std;

#define ArrSize 10

int elem = 0;

void input_score(double *);
void display_score(double *);
double cal_mean_score(double *);

int main()
{
    double golfScore[ArrSize];

    cout << "Enter golf scores(enter non number to quit)\n";
    input_score(golfScore);
    cout << "All golf score:\n";
    display_score(golfScore);
    cout << "Average golf score:" << cal_mean_score(golfScore) << endl;

    system("pause");
    return 0;
}
void input_score(double *arr)
{
    for (int i = 0; i < ArrSize; i++)
    {
        cout << "Input the " << i + 1
             << "-th golf score: ";
        if (cin >> arr[i])
        {
        }
        else
        {
            elem = i;
            break;
        }
        elem = i;
    }
}
void display_score(double *arr)
{
    for (int i = 0; i < elem; i++)
        cout << arr[i] << " ";
    cout << endl;
}
double cal_mean_score(double *arr)
{
    double average = 0.0;

    for (int i = 0; i < elem; i++)
        average += arr[i];

    return average / (double)elem;
}

运行结果:

在这里插入图片描述

3. box

下面是一个结构声明:

struct box
{
    char maker[40];
    float height;
    float width;
    float length;
    float volume;
};

a.编写一个函数,按值传递box结构,并显示每个成员的值。
b.编写一个函数,传递box结构的地址,并将volume成员设置为其他三维长度的乘积。
c.编写一个使用这两个函数的简单程序。

代码:

#include <iostream>
using namespace std;

struct box
{
    char maker[40];
    float height;
    float width;
    float length;
    float volume;
};

void display_box(box);
void cal_volume(box *);

int main()
{
    box example;

    cout << "Enter the name of maker:";
    cin.getline(example.maker, 40);
    cout << "Enter the height:";
    cin >> example.height;
    cout << "Enter the width:";
    cin >> example.width;
    cout << "Enter the length:";
    cin >> example.length;

    cal_volume(&example);
    display_box(example);

    system("pause");
    return 0;
}

void display_box(box b)
{
    cout << "maker:  " << b.maker << endl;
    cout << "height:  " << b.height << endl;
    cout << "width:  " << b.width << endl;
    cout << "length:  " << b.length << endl;
    cout << "volume:  " << b.volume << endl;
}

void cal_volume(box *b)
{
    b->volume = b->length * b->width * b->height;
}

运行结果:

在这里插入图片描述

4. 彩票

许多州的彩票发行机构都使用如程序清单7.4所示的简单彩票玩法的变体。在这些玩法中,玩家从一组被称为域号码(field number)的号码中选择几个。例如,可以从域号码1 ~ 47中选择5个号码;还可以从第二个区间(如1~27)选择一个号码(称为特选号码)。要赢得头奖,必须正确猜中所有的号码。中头奖的几率是选中所有域号码的几率与选中特选号码几率的乘积。例如,在这个例子中,中头奖的几率是从47个号码中正确选取5个号码的几率与从27个号码中正确选择1个号码的几率的乘积。请修改程序清单7.4,以计算中得这种彩票头奖的几率。

代码:

#include <iostream>
using namespace std;

long double probability(unsigned, unsigned);

int main()
{
    double field_total = 47, field_choices = 5;
    double special_total = 27, special_choices = 1;

    cout << "You have one chance in ";
    cout << probability(field_total, field_choices) * probability(special_total, special_choices);
    cout << " of winning.\n";

    system("pause");
    return 0;
}

long double probability(unsigned numbers, unsigned picks)
{
    long double result = 1.0;
    long double n;
    unsigned p;

    for (n = numbers, p = picks; p > 0; n--, p--)
    {
        result = result * n / p;
    }
    return result;
}

运行结果:

在这里插入图片描述

5. 阶乘

定义一个递归函数,接受一个整数参数,并返回该参数的阶乘。前面讲过,3的阶乘写作3!,等于32!,依此类推;而0!被定义为1。通用的计算公式是,如果n大于零,则n!=n(n-l)!。在程序中对该函数进行测试,程序使用循环让用户输入不同的值,程序将报告这些值的阶乘。

代码:

#include <iostream>
using namespace std;
long Factorial(int);
int main()
{

    int n;

    cout << "Enter a number n(n>0)(q to quit):";
    while (cin >> n)
    {
        cout << n << "! = " << Factorial(n) << endl;
        cout << "Next number(q to quit): ";
    }
    cout << "Done!\n";
    
    system("pause");
    return 0;
}

long Factorial(int n)
{
    if (n > 0)
        return n * Factorial(n - 1);
    return 1;
}

运行结果:

在这里插入图片描述

6. 数组操作

编写一个程序,它使用下列函数:
Fill_array()将一个double数组的名称和长度作为参数。它提示用户输入double值,并将这些值存储到数组中。当数组被填满或用户输入了非数字时,输入将停止,并返回实际输入了多少个数字。
Show_array()将一个double数组的名称和长度作为参数,并显示该数组的内容。
Reverse_array()将一个double数组的名称和长度作为参数,并将存储在数组中的值的顺序反转。程序将使用这些函数来填充数组,然后显示数组;反转数组,然后显示数组;反转数组中除第一个和最后一个元素之外的所有元素,然后显示数组。

代码:

#include <iostream>
using namespace std;

const unsigned int ArrSize = 20;

int Fill_array(double *, unsigned int);
void Show_array(const double array[], int length);
void Reverse_array(double Array[], int length);

int main()
{
    double arr[ArrSize];
    int arrLen = 0;

    cout << "Enter numbers(q to quit):" << endl;
    arrLen = Fill_array(arr, ArrSize);
    Show_array(arr, arrLen);
    Reverse_array(arr, arrLen);
    Show_array(arr, arrLen);

    system("pause");
    return 0;
}

int Fill_array(double array[], unsigned int ArrSize)
{
    int len = 0;

    while (cin >> array[len] && len < ArrSize)
        len++;

    return len;
}

void Show_array(const double array[], int length)
{
    if (length == 0)
    {
        cout << "The array is empty.\n";
        return;
    }
    cout << "Array content:\n";
    for (int i = 0; i < length; i++)
        cout << array[i] << " ";
    cout << endl;
}

void Reverse_array(double *Array, int length)
{
    if (length == 0)
    {
        cout << "The array is empty.\n";
        return;
    }
    cout << "Reverse all elements in the array except the first and last\n";
    for (int i = 0; i < length / 2; i++)
    {
        if (i == 0)
            continue;
        else
        {
            double temp = Array[i];
            Array[i] = Array[length - i - 1];
            Array[length - i - 1] = temp;
        }
    }
}

运行结果:

在这里插入图片描述

7. 数组处理函数

修改程序清单7.7中的3个数组处理函数,使之使用两个指针参数来表示区间。fill_array()函数不返回实际读取了多少个数字,而是返回一个指针,该指针指向最后被填充的位置;其他的函数可以将该指针作为第二个参数,以标识数据结尾。

代码:

#include <iostream>
using namespace std;

const int Max = 5;

double *fill_array(double *, double *);
void show_array(const double *, const double *);
void revalue(double, double *, double *);

int main()
{
    double properties[Max];
    double *end = fill_array(properties, properties + Max);

    show_array(properties, end);
    if (end != properties)
    {
        cout << "Enter revaluation factor: ";
        double factor;
        while (!(cin >> factor))
        {
            cin.clear();
            while (cin.get() != '\n')
            {
                continue;
            }
            cout << "Bad input; Please enter a number: ";
        }
        revalue(factor, properties, end);
        show_array(properties, end);
    }
    cout << "Done!\n";

    system("pause");
    return 0;
}

double *fill_array(double *begin, double *end)
{
    double *temp = begin;
    int i = 0;

    for (; temp != end; temp++)
    {
        cout << "Enter value #" << (i + 1) << ":";
        cin >> *temp;
        if (!cin)
        {
            cin.clear();
            while (cin.get() != '\n')
                continue;

            cout << "Bad input;Please enter a number:";
            break;
        }
        else if (*temp < 0)
            break;
        i++;
    }

    return temp;
}

void show_array(const double *begin, const double *end)
{
    int i = 0;

    for (; begin != end; begin++)
    {
        cout << "Property #" << (i + 1) << ": $";
        cout << *begin << endl;
        i++;
    }
}

void revalue(double r, double *begin, double *end)
{
    for (double *temp = begin; temp != end; temp++)
        *temp *= r;
}

运行结果:

在这里插入图片描述

在这里插入图片描述

8. 开支

在不使用array类的情况下完成程序清单7.15所做的工作。编写两个这样的版本:

a.使用const char * 数组存储表示季度名称的字符串,并使用double数组存储开支。
b.使用const char* 数组存储表示季度名称的字符串,并使用一个结构,该结构只有一个成员———个用于存储开支的double数组。这种设计与使用array类的基本设计类似。

a.

代码:

#include <iostream>
#include <string>
using namespace std;

const int Seasons = 4;
const string Snames[Seasons] = {"Spring", "Summer", "Fall", "Winter"};

void fill(double *);
void show(const double *);

int main()
{
    double expenses[Seasons];

    fill(expenses);
    show(expenses);

    system("pause");
    return 0;
}

void fill(double expenses[])
{
    for (int i = 0; i < Seasons; i++)
    {
        cout << "Enter " << Snames[i] << " expenses: ";
        cin >> expenses[i];
    }
}

void show(const double expenses[])
{
    double total = 0.0;

    cout << "\nEXPENSES\n";
    for (int i = 0; i < Seasons; i++)
    {
        cout << Snames[i] << ": $" << expenses[i] << endl;
        total += expenses[i];
    }
    cout << "Total Expenses: $" << total << endl;
}

运行结果:

在这里插入图片描述

b.

代码:

#include <iostream>
#include <string>
using namespace std;

const int Seasons = 4;
const string Snames[Seasons] = {"Spring", "Summer", "Fall", "Winter"};

typedef struct Expenses
{
    double expenses[Seasons];
} Expenses;

void fill(Expenses *e);
void show(const Expenses *e);

int main()
{
    struct Expenses e;

    fill(&e);
    show(&e);

    system("pause");
    return 0;
}

void fill(Expenses *e)
{
    for (int i = 0; i < Seasons; i++)
    {
        cout << "Enter " << Snames[i] << " expenses: ";
        cin >> e->expenses[i];
    }
}

void show(const Expenses *e)
{
    double total = 0.0;

    cout << "\nEXPENSES\n";
    for (int i = 0; i < Seasons; i++)
    {
        cout << Snames[i] << ": $" << e->expenses[i] << endl;
        total += e->expenses[i];
    }
    cout << "Total Expenses: $" << total << endl;
}

运行结果:

在这里插入图片描述

9. student

这个练习让您编写处理数组和结构的函数。下面是程序的框架,请提供其中描述的函数,以完成该程序。

#include <iostream>
using namespace std;

const int SLEN = 30;

struct student
{
    char fullname[SLEN];
    char hobby[SLEN];
    int ooplevel;
};
// getinfo () has two arguments: a pointer to the first element of
// an array of student structures and an int representing the
// number of elements of the array. The function solicits and
// stores data about students. It terminates input upon filling
// the array or upon encountering a blank line for the student
// name.The function returns the actual number of array elements
// filled.
int getinfo(student pa[], int n);
// display1 ( ) takes a student structure as an argument
// and displays its contents
void display1(student st);
// display2 () takes the address of student structure as an
// argument and displays the structure's contents
void display2(const student *ps);
// display3 () takes the address of the first element of an array
// of student structures and the number of array elements as
// arguments and displays the contents of the structures
void display3(const student pa[], int n);

int main()
{
    cout << "Enter class size: ";

    int class_size;
    cin >> class_size;

    while (cin.get  != '\n')
        continue;
    student *ptr_stu = new student[class_size];
    int entered = getinfo(ptr_stu, class_size);

    for (int i = 0; i < entered; i++)

    {
        display1(ptr_stu[i]);

        display2(&ptr_stu[i]);
    }
    display3(ptr - stu, entered);

    delete[] ptr_stu;
    cout << "Done\n";
    return 0;
}

代码:

#include <iostream>
using namespace std;

const int SLEN = 30;

struct student
{
    char fullname[SLEN];
    char hobby[SLEN];
    int ooplevel;
};
// getinfo () has two arguments: a pointer to the first element of
// an array of student structures and an int representing the
// number of elements of the array. The function solicits and
// stores data about students. It terminates input upon filling
// the array or upon encountering a blank line for the student
// name.The function returns the actual number of array elements
// filled.
int getinfo(student pa[], int n);
// display1 ( ) takes a student structure as an argument
// and displays its contents
void display1(student st);
// display2 () takes the address of student structure as an
// argument and displays the structure's contents
void display2(const student *ps);
// display3 () takes the address of the first element of an array
// of student structures and the number of array elements as
// arguments and displays the contents of the structures
void display3(const student pa[], int n);

int main()
{
    cout << "Enter class size: ";
    int class_size;
    cin >> class_size;
    while (cin.get() != '\n')
        continue;

    student *ptr_stu = new student[class_size];
    int entered = getinfo(ptr_stu, class_size);
    for (int i = 0; i < entered; i++)
    {
        display1(ptr_stu[i]);
        display2(&ptr_stu[i]);
    }
    display3(ptr_stu, entered);
    delete[] ptr_stu;
    cout << "Done\n";

    system("pause");
    return 0;
}

int getinfo(student pa[], int n)
{
    int i;

    cout << "Please input the students information:" << endl;
    for (i = 0; i < n; i++)
    {
        cout << "Student #" << i + 1 << ": " << endl;
        cout << "Fullname: ";
        cin.getline(pa[i].fullname, SLEN);
        if (pa[i].fullname[0] == '\0')
            break;
        cout << "Hobby: ";
        if (pa[i].hobby[0] == '\0')
            break;
        cin.getline(pa[i].hobby, SLEN);
        cout << "Ooplevel: ";
        if (!(cin >> pa[i].ooplevel))
            break;
        cin.get();
    }
    cout << "Enter End!" << endl;
    return i;
}

void display1(student st)
{
    cout << "fullname:" << st.fullname << "     hobby:" << st.hobby << "    opplevel:" << st.ooplevel << endl;
}

void display2(const student *ps)
{
    cout << "fullname:" << ps->fullname << "     hobby:" << ps->hobby << "    opplevel:" << ps->ooplevel << endl;
}

void display3(const student pa[], int n)
{
    for (int i = 0; i < n; i++)
    {
        cout << "Student #" << i + 1 << endl;
        cout << "fullname:" << pa[i].fullname << "     hobby:" << pa[i].hobby << "    opplevel:" << pa[i].ooplevel << endl;
    }
}

运行结果:

在这里插入图片描述

10. calculate()

设计一个名为calculate()的函数,它接受两个double值和一个指向函数的指针,而被指向的函数接受两个double参数,并返回一个double 值。calculate()函数的类型也是double,并返回被指向的函数使用calculate()的两个double参数计算得到的值。例如,假设add()函数的定义如下:

double add (double x, double y)
{
	return x+ y;
}

则下述代码中的函数调用将导致calculate()把2.5和10.4传递给add( )函数,并返回add()的返回值(12.9):

double q = calculate(2.5, 10.4,  add);

请编写一个程序,它调用上述两个函数和至少另一个与add()类似的函数。该程序使用循环来让用户成对地输入数字。对于每对数字,程序都使用calculate( )来调用add( )和至少一个其他的函数。如果读者爱冒险,可以尝试创建一个指针数组,其中的指针指向add()样式的函数,并编写一个循环,使用这些指针连续让 calculate()调用这些函数。提示:下面是声明这种指针数组的方式,其中包含三个指针:

double (*pf [3]) (double, double);

可以采用数组初始化语法,并将函数名作为地址来初始化这样的数组。

代码:

#include <iostream>
using namespace std;

double add(double, double);
double subtract(double, double);
double multiply(double, double);
double calculate(double, double, double (*func)(double, double));

int main(void)
{
    double x, y;
    double (*pf[3])(double, double) = {add, subtract, multiply};

    cout << "Enter two numbers(q to quit):";
    while (cin >> x >> y)
    {
        for (int i = 0; i < 3; i++)
        {
            switch (i)
            {
            case 0:
                cout << x << "+" << y << "=" << calculate(x, y, pf[i]) << endl;
                break;
            case 1:
                cout << x << "-" << y << "=" << calculate(x, y, pf[i]) << endl;
                break;
            case 2:
                cout << x << "*" << y << "=" << calculate(x, y, pf[i]) << endl;
                break;
            }
        }
        cout << "Enter two numbers(q to quit):";
    }
    cout << "Done!\n";

    system("pause");
    return 0;
}

double add(double x, double y)
{
    return x + y;
}

double subtract(double x, double y)
{
    return x - y;
}

double multiply(double x, double y)
{
    return x * y;
}

double calculate(double x, double y, double (*func)(double, double))
{
    return (*func)(x, y);
}

运行结果:

在这里插入图片描述

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

UestcXiye

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值