7.1 编写一个程序,不断要求用户输入两个数,直到其中一个为0,对于每两个数,程序将使用一个函数来计算它们的调和平均数,并将结果返回给main(),而后者将报告结果。调和平均数=2.0*x*y/(x+y)。
#include <iostream>
#include <array>
using namespace std;
double tiaoheAverage(double x, double y)
{
double ret;
ret = 2.0 * x * y/(x+y);
return ret;
}
int main(int argc, char *argv[])
{
cout<<"请输入两个数:"<<endl;
double input1, input2;
double output;
cin>>input1>>input2;
while((input1 != 0) && (input2 != 0) )
{
output = tiaoheAverage(input1, input2);
cout<<"两个数的调和平均数="<<output<<endl;
cout<<"请继续输入两个数:"<<endl;
cin>>input1>>input2;
}
return 0;
}
7.2 编写一个程序,要求用户输入最多10个高尔夫成绩,并将其存入到一个数组中。程序允许用户提早结束输入,并在一行上显示所有成绩,然后报告平均成绩。请使用3个数组处理函数来分别进行输入、显示和计算平均成绩。 //用参数传递输入值
#include <iostream>
#include <array>
using namespace std;
int maxSixe = 10;
void inputScore(double *score, int *num);
void displayScore(double *score, int num);
double coutAverage(double *score, int num);
int main(int argc, char *argv[])
{
int num;
double score[maxSixe];
inputScore(score, &num);
cout<<"你输入了"<<num<<"个数"<<endl;
displayScore(score, num);
double average = coutAverage(score, num);
cout<<"输入所有分数的平均值是:"<<average<<endl;
return 0;
}
void inputScore(double *score, int *num)
{
int i = 0;
for(; i<10; i++)
{
cout<<"请输入第"<<i+1 <<"个分数, 想要结束可以输入一个字母:"<<endl;
if(cin >> score[i])
{
}
else
{
*num = i;
break;
}
*num = i + 1;
}
return;
}
void displayScore(double *score, int num)
{
cout<<"输入的"<<num <<"个分数分别是:"<<endl;
for(int i = 0; i < num; i++)
{
cout<<score[i];
if(i != num -1)
{
cout<<",";
}
else
{
cout<<endl;
}
}
}
double coutAverage(double *score, int num)
{
double average, sum = 0;
for(int i = 0; i < num; i++)
{
sum = sum + score[i];
}
return sum/num;
}
7.6 编写一个程序,它使用下列函数:
Fill_array()将一个double数组的名称和长度作为参数。它提示用户输入double值,并将这些值存储到数组中。当数组被填满或用户输入了非数字时,输入将停止,并返回实际输入了多少个数字。
Show_array()将一个double数组的名称和长度作为参数,并显示该数组的内容。
Reverse_array()将一个double数组的名称和长度作为参数,并将存储在数组中的值的顺序反转。
程序将使用这些函数来填充数组,然后显示数组;反转数组,然后显示数组;反转数组中除第一个和最后一个元素之外的所有元素, 然后显示数组。
#include <iostream>
#include <array>
using namespace std;
int maxSixe = 10;
int Fill_array(double score[], int size);
void Show_array(double score[], int num);
void Reverse_array(double score[], int num);
int main(int argc, char *argv[])
{
int num;
double score[maxSixe];
num = Fill_array(score, maxSixe);
cout<<"你输入了"<<num<<"个数"<<endl;
Show_array(score, num);
Reverse_array(score, num);
cout<<"反转后的数组值分别是:";
for (size_t i = 0; i < num; i++)
{
cout<<score[i];
if(i != num -1)
{
cout<<", ";
}
else
{
cout<<endl;
}
}
return 0;
}
int Fill_array(double score[], int size)
{
int i = 0;
int num;
for(; i< size; i++)
{
cout<<"请输入第"<<i+1 <<"个分数, 想要结束可以输入一个字母:"<<endl;
if(cin >> score[i])
{
}
else
{
num = i;
break;
}
num = i + 1;
}
return num;
}
void Show_array(double score[], int num)
{
cout<<"输入的"<<num <<"个分数分别是:";
for(int i = 0; i < num; i++)
{
cout<<score[i];
if(i != num -1)
{
cout<<", ";
}
else
{
cout<<endl;
}
}
}
void Reverse_array(double score[], int num)
{
double tmp;
for(int i = 0; i < num/2; i++)
{
tmp = score[i];
score[i] = score[num - 1 -i];
score[num - 1 -i] = tmp;
}
}
7.7修改程序清单7.7中的3个数组处理函数,使之使用两个指针参数来表示区间。file_array()函数不返回实际读取了多少个数字,而是返回一个指针,该指针指向最后被填充的位置。其他的函数可以将该指针作为第二个参数,以标识数据结尾。
#include <iostream>
using namespace std;
const int Max = 5;
// function prototypes
double* fill_array(double *begin, double *end);
void show_array(double *begin, double *end); // don't change data
void revalue(double r, double *begin, double *end);
int main()
{
double properties[Max];
double* endaddress = NULL;
endaddress = fill_array(&properties[0], &properties[Max - 1]);
show_array(properties, endaddress);
if (endaddress != NULL)
{
cout << "Enter revaluation factor: ";
double factor;
while (!(cin >> factor)) // bad input
{
cin.clear();
while (cin.get() != '\n')
continue;
cout << "Bad input; Please enter a number: ";
}
revalue(factor, &properties[0], endaddress);
show_array(&properties[0], endaddress);
}
cout << "Done.\n";
// cin.get();
// cin.get();
return 0;
}
double* fill_array(double *begin, double *end)
{
double *temp;
for (temp = begin; temp <= end; temp++)
{
cout << "Enter value #" <<temp-begin + 1 << ": ";
cin >> *temp;
if (!cin) // bad input
{
cin.clear();
while (cin.get() != '\n')
{
continue;
}
cout << "Bad input; input process terminated.\n";
break;
}
else if (*temp < 0) // signal to terminate
{
break;
}
}
if(temp == begin)
{
return NULL;
}
else
{
return temp - 1;
}
}
// the following function can use, but not alter,
// the array whose address is ar
void show_array(double *begin, double *end)
{
double *temp;
int i = 0;
for (temp = begin, i = 0; temp <= end; temp++,i++)
{
cout << "Property #" << (i + 1) << ": $";
cout << *temp << endl;
}
}
// multiplies each element of ar[] by r
void revalue(double r, double *begin, double *end)
{
double *temp;
int i = 0;
for (temp = begin, i = 0; temp <= end; temp++,i++)
{
*temp *= r;
}
}
7.8.在不使用array类的情况下完成程序清单7.15所做的工作。编写两个这样的版本:
a.使用const char *数组存储表示季度名称的字符串,并使用double数组存储开支。
b.使用const char *数组存储表示季度名称的字符串,并使用一个结构,该结构只有一个成员——一个用于存储开支的double数组。这种设计与使用array类基本设计类似
/*--------------------a.-------------------*/
#include <iostream>
#include <string>
const int Seasons = 4;
const char *Snames[] = {"Spring", "Summer", "Fall", "Winter"};
void fill(double *pa);
void show(double *pa);
int main()
{
double expenses[Seasons];
fill(expenses);
show(expenses);
return 0;
}
void fill(double *pa)
{
for (int i = 0; i < Seasons; i++)
{
std::cout << "Enter " << Snames[i] << " expenses: ";
std::cin >> (pa)[i];
}
}
void show(double *da)
{
double total = 0.0;
std::cout << "\nEXPENSES\n";
for (int i = 0; i < Seasons; i++)
{
std::cout << Snames[i] << ": $" << da[i] << '\n';
total += da[i];
}
std::cout << "Total: $" << total << '\n';
}
/*--------------------b.-------------------*/
#include <iostream>
#include <string>
const int Seasons = 4;
const char *Snames[] = {"Spring", "Summer", "Fall", "Winter"};
struct str_expenses
{
double expenses[Seasons];
};
void fill(str_expenses *pa);
void show(str_expenses *pa);
int main()
{
str_expenses expensestmp;
fill(&expensestmp);
show(&expensestmp);
return 0;
}
void fill(str_expenses *pa)
{
for (int i = 0; i < Seasons; i++)
{
std::cout << "Enter " << Snames[i] << " expenses: ";
std::cin >> pa->expenses[i];
}
}
void show(str_expenses *da)
{
double total = 0.0;
std::cout << "\nEXPENSES\n";
for (int i = 0; i < Seasons; i++)
{
std::cout << Snames[i] << ": $" << da->expenses[i] << '\n';
total += da->expenses[i];
}
std::cout << "Total: $" << total << '\n';
}
7.9.这个练习让您编写处理数组和结构的函数。下面是程序的框架,请提供其中描述的函数,以完成该程序。
#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);
cout<<"你总共正确输入了"<<entered<<"个"<<endl;
for (int i = 0; i < entered; i++)
{
cout<<"display1显示输入第"<<i+1<<"个学生的信息"<<endl;
display1(ptr_stu[i]);
cout<<"display2显示输入第"<<i+1<<"个学生的信息"<<endl;
display2(&ptr_stu[i]);
}
cout<<"-----------------------------------"<<endl;
display3(ptr_stu, entered);
delete[] ptr_stu;
cout << "Done\n";
return 0;
}
int getinfo(student pa[], int n)
{
int i = 0;
for(; i < n; i++)
{
cout<<"请输入第"<< i+1<<"个学生的信息:"<<endl;
cout<<"fullname:";
cin>>pa[i].fullname;
cout<<"hobby:";
cin>>pa[i].hobby;
cout<<"ooplevel:";
cin>>pa[i].ooplevel;
if(!cin)
{
cin.clear();
while(cin.get() != '\n')
continue;
cout<<"输入错误,程序结束"<<endl;
break;
}
}
return i;
}
void display1(student st)
{
cout << "name: " << st.fullname << endl;
cout << "hobby: " << st.hobby << endl;
cout << "ooplevel: " << st.ooplevel << endl;
}
void display2(const student* ps)
{
cout << "name: " << ps->fullname << endl;
cout << "hobby: " << ps->hobby << endl;
cout << "ooplevel: " << ps->ooplevel << endl;
}
void display3(const student pa[], int n)
{
for(int i = 0; i < n; i++)
{
cout<<"display3显示输入第"<<i+1<<"个学生的信息"<<endl;
// display2(&pa[i]);
cout << "name: " << pa[i].fullname << endl;
cout << "hobby: " << pa[i].hobby << endl;
cout << "ooplevel: " << pa[i].ooplevel << endl;
}
}
7.10 设计一个名为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;
typedef double (*pfunc)(double x, double y);
double add(double x, double y)
{
return x + y;
}
double myminus(double x, double y)
{
return x - y;
}
double calculate(double x, double y, pfunc pf)
{
return pf(x, y);
}
double (*pf[3]) (double, double);
int main()
{
for(;;)
{
cout<<"想要求两数的和和差,请成对输入两个数:";
double x, y;
if(cin >> x>> y)
{
cout<<"两个数的和是:"<<calculate (x, y, add)<<endl;
cout<<"两个数的差是:"<<calculate (x, y, myminus)<<endl;
}
else
{
cout<<"您输入的值无效"<<endl;
cin.clear();
cin.sync();
}
}
return 0;
}