C Primer Plus (第六版) 第十二章_编程练习答案
程序员文章站
2022-07-04 16:03:20
...
no1.c
//不使用全局变量,重写程序清单12.4
# include <stdio.h>
void critic(int * pti);
int main(void)
{
int units ;
printf("How many pounds to a firkin of butter?\n");
scanf("%d" , &units);
while(units != 56)
critic(&units);
printf("You must have looked it up!\n");
return 0 ;
}
void critic(int * pti)
{
printf("No luck , my friend.Try again.\n");
scanf("%d" , pti);
}
no2.c
//在美国,通常以英里/加仑来计算油耗;在欧洲,以升/100公里来计算.下面是程序的一部分,提示
//用户选择计算模式(美制或公制),然后接收数据并计算油耗.
//pel2-2b.c
//与 pel2-2a.c一起编译
# include <stdio.h>
# include "pel2-2a.h"
int main(void)
{
int mode ;
printf("Enter 0 for metric mode, 1 for US mode :");
scanf("%d" , &mode) ;
while (mode >= 0)
{
set_mode(mode) ;
get_info();
show_info();
printf("Enter 0 for metric mode , 1 for US mode");
printf("(-1 to quit):");
scanf("%d" , &mode);
}
printf("Done.\n");
return 0 ;
}
/*pel2-2a.c*/
/*与no2.c一起编译*/
# include <stdio.h>
static int mode ;
static double juli ;
static double youliang ;
void set_mode(int m)
{
if (m > 1)
{
printf("Invalid mode specified. Mode %d(US) used.\n" , mode);
return ;
}
mode = m ;
}
void get_info(void)
{
switch (mode)
{
case 0 :
printf("Enter distance traveled in kilometers:");
scanf("%lf" , &juli);
printf("Enter fuel consumed in liters:");
scanf("%lf" , &youliang);
break ;
case 1 :
printf("Enter distance traveled in miles:");
scanf("%lf" , &juli);
printf("Enter fuel consumed in gallons:");
scanf("%lf" , &youliang);
break ;
}
}
void show_info(void)
{
double youhao = 0 ;
switch (mode)
{
case 0 :
youhao = youliang / (juli / 100) ;
printf("Fuel consumption is %.2lf liters per 100 km.\n" , youhao);
break ;
case 1 :
youhao = juli / youliang ;
printf("Fuel consumption is %.2lf miles per gallon.\n" , youhao);
break ;
}
}
/*pel2-2a.h*/
/*同文件夹下包含此头文件*/
void set_mode(int mode);
void get_info(void);
void show_info(void);
no3.c
//重新设计编程练习2,要求只使用自动变量.该程序提供的用户界面不变,即提示用户输入模式等.
//但是函数调用要作相应变化
# include <stdio.h>
# include "pel3-3a.h"
int main(void)
{
int mode ;
int t_mode ;
double juli ;
double youliang ;
printf("Enter 0 for metric mode, 1 for US mode :");
scanf("%d" , &t_mode) ;
while (t_mode >= 0)
{
set_mode(&mode , t_mode) ;
get_info(mode , &juli , &youliang);
show_info(mode , juli , youliang);
printf("Enter 0 for metric mode , 1 for US mode");
printf("(-1 to quit):");
scanf("%d" , &t_mode);
}
printf("Done.\n");
return 0 ;
}
/*pel3-3a.c*/
/*与no3.c一起编译*/
# include <stdio.h>
void set_mode(int * mode , int n)
{
if (n > 1)
{
printf("Invalid mode specified. Mode %d(US) used.\n" , *mode);
return ;
}
*mode = n ;
}
void get_info(int mode , double * juli , double * youliang)
{
switch (mode)
{
case 0 :
printf("Enter distance traveled in kilometers:");
scanf("%lf" , juli);
printf("Enter fuel consumed in liters:");
scanf("%lf" , youliang);
break ;
case 1 :
printf("Enter distance traveled in miles:");
scanf("%lf" , juli);
printf("Enter fuel consumed in gallons:");
scanf("%lf" , youliang);
break ;
}
}
void show_info(int mode , double juli , double youliang)
{
double youhao = 0 ;
switch (mode)
{
case 0 :
youhao = youliang / (juli / 100) ;
printf("Fuel consumption is %.2lf liters per 100 km.\n" , youhao);
break ;
case 1 :
youhao = juli / youliang ;
printf("Fuel consumption is %.2lf miles per gallon.\n" , youhao);
break ;
}
}
/*pel3-3a.h*/
/*同文件夹下包含此文件*/
void set_mode(int * mode , int n);
void get_info(int mode , double * juli , double * youliang);
void show_info(int mode , double juli , double youliang);
no4.c
//在一个 循环中编写并测试一个函数,该函数返回他被调用的次数.
# include <stdio.h>
int count(void);
int main(void)
{
int loop ;
printf("Please enter the loop :");
scanf("%d" , &loop);
for (int i = 0 ; i < loop ; i++)
printf("count = %d\n" , count()) ;
return 0 ;
}
int count(void)
{
static int count = 1;
return count++ ;
}
no5.c
//编写一个程序,生成100个1~10范围内的随机数,并以降序排列(可以把11章的排序算法稍加改动
//便可用于整数排序,这里仅对整数排序)
# include <stdio.h>
# include <stdlib.h>
# include <time.h>
# define SIZE 100
# define L_LIMIT 1
# define U_LIMIT 100
int rnd(int lower , int upper);
void sort(int arr[] , int n);
int main(void)
{
int ar[SIZE] ;
srand((unsigned)time(NULL));
printf("生成的%d个随机数如下:\n" , SIZE);
for (int i = 0 ; i < SIZE ; i++)
{
ar[i] = rnd(L_LIMIT , U_LIMIT);
printf("%5d " , ar[i]);
if (((i + 1) % 10) == 0)
putchar('\n');
}
sort(ar , SIZE);
printf("\n按降序排列如下:\n");
for (int i = 0 ; i < SIZE ; i++)
{
printf("%5d " , ar[i]);
if (((i + 1) % 10) == 0)
putchar('\n');
}
return 0 ;
}
int rnd(int lower , int upper)
{
int ret_rand ;
ret_rand = (rand() % (upper - lower + 1)) + lower ;
return ret_rand ;
}
void sort(int arr[] , int n)
{
for (int i = 0 ; i < n - 1 ; i++)
for (int j = 0 ; j < n - i - 1 ; j++)
{
if (arr[j] < arr[j + 1])
{
int tmp ;
tmp = arr[j] ;
arr[j] = arr[j + 1] ;
arr[j + 1] = tmp ;
}
}
}
no6.c
//编写一个程序,生成100个1~10范围内的随机数,并以降序排列(可以把11章的排序算法稍加改动
//便可用于整数排序,这里仅对整数排序)
# include <stdio.h>
# include <stdlib.h>
# include <time.h>
# define SIZE 100
# define L_LIMIT 1
# define U_LIMIT 100
int rnd(int lower , int upper);
void sort(int arr[] , int n);
int main(void)
{
int ar[SIZE] ;
srand((unsigned)time(NULL));
printf("生成的%d个随机数如下:\n" , SIZE);
for (int i = 0 ; i < SIZE ; i++)
{
ar[i] = rnd(L_LIMIT , U_LIMIT);
printf("%5d " , ar[i]);
if (((i + 1) % 10) == 0)
putchar('\n');
}
sort(ar , SIZE);
printf("\n按降序排列如下:\n");
for (int i = 0 ; i < SIZE ; i++)
{
printf("%5d " , ar[i]);
if (((i + 1) % 10) == 0)
putchar('\n');
}
return 0 ;
}
int rnd(int lower , int upper)
{
int ret_rand ;
ret_rand = (rand() % (upper - lower + 1)) + lower ;
return ret_rand ;
}
void sort(int arr[] , int n)
{
for (int i = 0 ; i < n - 1 ; i++)
for (int j = 0 ; j < n - i - 1 ; j++)
{
if (arr[j] < arr[j + 1])
{
int tmp ;
tmp = arr[j] ;
arr[j] = arr[j + 1] ;
arr[j + 1] = tmp ;
}
}
}
no7.c
//编写一个程序,按照程序清单12.13输出实例后面讨论的内容,修改程序.使其输出类似:
//Enter the number of sets ; enter q to stop : 18
//How many sides and how many dice? 6 3
//her are 18 sets of 3 6-sided throws.
// 12 10 6 9 8 14 8 15 9 14 12 17 11 7 10 13 8 14
//How many sets? Enter q to stop : q
# include <stdio.h>
# include <stdlib.h>
# include <time.h>
# include "no7_diceroll.h"
int main(void)
{
int dice , roll ;
int sides ;
int sets = 0 ;
int status ;
srand((unsigned int) time(NULL)) ;
printf("Enter the number of sets; Enter q to stop.\n");
while (scanf("%d" , &sets) && sets > 0)
{
printf("How many sides and how may dice?\n");
if ((status = scanf("%d %d" , &sides , &dice)) < 2)
{
if (status == EOF)
break ;
else
{
printf("You should have entered an integer.");
printf(" Let's begin again.\n");
while (getchar() != '\n')
continue ;
printf("How many sides and how may dice?\n");
continue ;
}
}
printf("Here are %d sets of %d %d-sided throws.\n" ,
sets , dice , sides);
for (int i = 0 ; i < sets ; i++)
{
roll = roll_n_dice(dice , sides) ;
printf("%d " , roll);
}
putchar('\n');
printf("How many sets? Enter q to stop.\n");
}
printf("The rollem() function was called %d times.\n" , roll_count);
printf("GOOD FORTUNE TO YOU !\n");
return 0 ;
}
/*no7_diceroll.c*/
/*与no7.c一起编译*/
# include "no7_diceroll.h"
# include <stdio.h>
# include <stdlib.h>
int roll_count = 0 ;
static int rollem(int sides)
{
int roll;
roll = rand() % sides + 1 ;
++roll_count ;
return roll ;
}
int roll_n_dice(int dice , int sides)
{
int d ;
int total = 0;
if (sides < 2)
{
printf("Need at least 2 sides.\n");
return -2 ;
}
if (dice < 1)
{
printf("Need at least 1 die.\n");
return -1 ;
}
for (d = 0 ; d < dice ; d++)
total += rollem(sides) ;
return total ;
}
/*no7_diceroll.h*/
/*同文件夹下包含此文件*/
extern int roll_count ;
int roll_n_dice(int dice , int sides) ;
no8.c
//下面是程序的一部分:
# include <stdio.h>
# include <stdlib.h>
int * make_array(int elem , int val) ;
void show_array(const int ar[] , int n);
int main(void)
{
int * pa ;
int size ;
int value ;
printf("Enter the number of elements: ");
while (scanf("%d" , &size) == 1 && size > 0)
{
printf("Enter the initialization value: ");
scanf("%d" , &value);
pa = make_array(size , value);
if (pa)
{
show_array(pa , size);
free(pa);
}
printf("Enter the number of elements (<1 to quit) : ");
}
printf("Done.\n");
return 0 ;
}
//提供make_array()和show_array()函数定义,完成程序.make_array()函数接受两个参数,
//第一个参数是int类型数组的元素个数,第二个参数是要赋给每个元素的值.该函数调用
//malloc()创建一个大小合适的数组,将其每个元素设置为指定的值,并返回一个指向该数组
//的指针.show_array()函数显示数组的内容,一行显示8个.
int * make_array(int elem , int val)
{
int * ret_par;
ret_par = (int *)malloc(elem * sizeof(int)) ;
for (int * pt = ret_par ; pt < ret_par + elem ; pt++)
*pt = val ;
return ret_par ;
}
void show_array(const int ar[] , int n)
{
for (int i = 0 ; i < n ; i++)
{
printf("%d " , ar[i]);
if (((i + 1) % 8) == 0)
putchar('\n');
}
putchar('\n');
}
no9.c
//编写一个符合以下描述的函数.首先,询问用户需要输入多少个单词.然后,接受用户输入的单词
//并显示出来,使用malloc()并回答第一个问题(即输入多少个单词),创建一个动态数组,该数组
//内含相应的指向char的指针(注意,由于数组的每个元素都是指向char的指针,所以用于储存
//malloc()返回值的指针应该是指向一个指针的指针,且它所指向的指针指向char).在读取字符
//串时,该程序应该把单词读入一个临时的char数组,使用malloc()分配足够的储存空间来储存单
//词,并把地址存入该指针数组(该数组中每个元素都是指向char的指针).然后,从临时数组中把
//单词拷贝到动态分配的储存空间中.因此,有一个字符指针数组,每个指针都指向一个对象,该对
//象的大小正好能容纳被储存的特定单词.下面是程序的运行实例.
//How many words do you wish to enter? 5
//Enter 5 words now :
//I enjoyed doing this exercise
//Here are your words:
//I
//enjoyed
//doing
//this
//exercise
# include <stdio.h>
# include <stdlib.h>
# include <string.h>
int main(void)
{
char ** par_ch ;
char * words ;
char tmp_arr_ch[100] ;
int count ;
printf("How many words do you wish to enter? ");
scanf("%d" , &count);
// 这里很费解,我调试了很久,我把我的理解写在这里
// 首先我们的目的是让计算机给我们分配指定数量的空间
// 我们分配多大?一个指针需要多大空间? 4 个字节
// 那么连续的4个字节才是一个完整的地址变量,
// 所以此刻用char * 类型去指向这4个字节显然是不对的
// char * 是用来指向 char 类型的,char * 的移动单元是一个字节,
// 4个字节才是一个完整的地址数据,用char * 指着其中某一个字节读数据,显然不对
// 所以我们要再用一个指向char * 类型指针,来指向分配的空间
// 此刻我们就得到了 char **指针类型,即 指向字符指针的指针
// 分析一下,char * 看做变量,那么指向他的变量只能是 char * (char *)
par_ch = (char **)malloc(count * sizeof(char *)) ;
printf("Enter %d words now:\n" , count);
for (int i = 0 ; i < count ; i++)
{
scanf("%s" , tmp_arr_ch);
words = (char *)malloc((strlen(tmp_arr_ch) + 1) * sizeof(char));
strcpy(words , tmp_arr_ch);
par_ch[i] = words ;
}
puts("Here are your words:");
for (int i = 0 ; i < count ; i++)
{
puts(par_ch[i]);
free(par_ch[i]);
}
free(par_ch);
return 0 ;
}