码迷,mamicode.com
首页 > 其他好文 > 详细

C Primer Plus (第五版) 第十六章 C预处理器和C库 编程练习

时间:2015-06-12 22:26:41      阅读:291      评论:0      收藏:0      [点我收藏+]

标签:c primer plus   (第五版   ) 第十六章   编程练习   c预处理器和c库   

第十六章 C预处理器和C库


  1. 开发一个包含您需要使用的预处理器定义的头文件

//max.h 
#ifndef _MAX_H_
    #define _MAX_H_
    #define MAX(X, Y) ((X)>(Y)?(X):(Y))
#endif


2.两个数的调和平均数可用如下方法得到:首先对两数的倒数取平均值,最后再取倒数。使用#define指令定义一个宏“函数”执行这个运算。编写一个简单的程序测试该宏。

#include <stdio.h>
#define HARMONIC_AVERAGEh(x, y) (1 / ((1/(x) + 1/(y)) /2))
//书上的答案,两个数的积的二倍除以两个数的和等于这两个数的调和平均数
//读书少,很多数学问题不懂,唉!!!!
#define HMEAN(X,Y) (2.0 * (X) *(Y) / ((X) + (Y)))
int main(void)
{
	double x, y, z;

	x = 3;
	y = 9;
	z = HARMONIC_AVERAGEh(x, y);
	printf("%.2lf %.2lf的调和平均数是:%.2lf\n", x, y, z);
	printf("%.2lf %.2lf的调和平均数是:%.2lf\n", x, y, HMEAN(x, y));
	return 0;
}


3.极坐标用向量的长度和向量相对于x轴的逆时针转角来描述该向量。直角坐标用向量的x和y坐标来描述该向量(请参见图16.3)。编写程序,它读取向量的长度和角度(以度表示)然后显示x和y坐标。相关等式如下:

x = r cos A y = r sin A

要完成这个转换,需要使用一个函数,该函数接受一个包含极坐标的结构作为参数,返回一个包含直角坐标的结构(也可使用指向结构的指针)。

技术分享

//完全是道数学题,不知道是否做对
#include <stdio.h>
#include <math.h>
#define PI 3.141592654

struct  polar{
	double len;
	double angle;
};
struct tect{
	double x;
	double y;
};
struct tect PolarToTect(const struct polar * p);
int main(void)
{
	struct  polar input;
	struct tect result;
	printf("Enter vector length and angle:");
	scanf("%lf%lf", &input.len, &input.angle);
	result = PolarToTect(&input);
	printf("polar: %.2lf %.2lf\n", input.len, input.angle);
	printf("result: %.2lf %.2lf\n", result.x, result.y);

	return 0;
}
struct tect PolarToTect(const struct polar * p)
{
	struct tect temp;
	//书上的答案为什么这里要求度数而不直角用输入的度数?
	//读书少不懂,就当是直角坐标需要吧。
	double ang = PI / 180 * p->angle;
	temp.x = p->len * acos(ang);
	temp.y = p->len * asin(ang);

	return temp;
}


4.ANSI库这样描述clock()函数:

  #include <time.h>

  clock_t clock(void);

  clock_t是在time.h中定义的类型。clock()函数返回处理器时间,其单位依赖于实现(如果无法得到或无法表示处理器时钟,该函数返回-1).而同样在time.h中定义的CLOCKS_PER_SEC是每秒的处理器时间单位个数。因此,求出两次调用函数clock()的返回值差,再用CLOCKS_PER_SEC去除这个差值,结果就是以秒为单位的两次调用之间的时间间隔。在做除法之前,将值的类型指派为double类型,可以将时间精确到小数点以后。编写一个函数,接受一个时间延迟数作为参数,然后运行一个循环,直至这段时间过完。编写一个简单的程序测试该函数。

#include <stdio.h>
#include <time.h>

void delay(int time);

int main(void)
{
	int t;

	printf("请输入要延时的时间以秒为单位,输入字母Q退出:");
	while (scanf("%d", &t) == 1)
	{
		delay(t);
		printf("时间到。\n");
		printf("请输入要延时的时间以秒为单位,输入字母Q退出:");
	}

	return 0;
}

void delay(int time)
{
	double i;
	//i的值是执行到这条语句时程序运行的秒数
	i = (double)clock() / CLOCKS_PER_SEC;
	while ((double)clock() / CLOCKS_PER_SEC - i < time)
		;
}


5.编写一个函数。访函数接受下列参数:一个int数组的名称,数组大小和一个代表选取次数的值。然后函数从数组中随机选择指定数量的元素并打印它们。每个元素最多选择一次(摸拟抽奖或挑选陪审成员)。另外,如果您的实现支持time()(在第12章中介绍)或其他类似函数,可在srand()中使用这个函数的输出来初始化随机数生成器rand()。编写一个简单的程序测试该函数。

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define NUM 36
void fun(int * pa, int n, int b);

int main(void)
{
	int a[NUM];
	int i, num;

	for (i = 0; i < NUM; i++)
		a[i] = i + 1;
	srand((unsigned)time(NULL));
	printf("请输入个数:");
	while (scanf("%d", &num) == 1 && num > 0 && num <= NUM)
	{
		fun(a, NUM, num);
		printf("请输入个数:");
	}
	return 0;
}

void fun(int * pa, int n, int b)
{
	int len, temp;

	do
	{
		len = rand() % n;
		printf("%3d", pa[len]);
		if (len == n + 1)
			n--;
		else
		{
			temp = pa[n];
			pa[n] = pa[len];
			pa[n] = temp;
			n--;
		}
	} while (--b);
	printf("\n");
}


6.修改程序清单16.15使其使用struct names元素(在程序清单后定义)组成的数组,而不是使用用double数组,使用较少元素并显式初始化数组为由合适名字组成的数组。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define NUM 6

struct names{
	char first[12];
	char last[12];
};
void showarray(struct names ar[], int n);
int mycomp(const void *p1, const void *p2);



int main(void)
{
	struct names name[NUM] ={
		{ { "dehua" }, { "liu" } },
		{ { "xueiyou" }, { "zhang" } },
		{ { "fucheng" }, { "guo" } },
		{ { "jahun" }, { "zhang" } },
		{ { "jahun" }, { "liang" } },
		{ { "chaowei" }, { "liang" } }
	};//不光英文不懂,拼音也好烂

	puts("Random list: ");
	showarray(name, NUM);
	qsort(name, NUM, sizeof(struct names), mycomp);
	puts("\nSorted list: ");
	showarray(name, NUM);

	return 0;
}

void showarray(struct names * pname, int n)
{
	int index;

	for (index = 0; index < n; index++)
	{
		printf("%s.%s", pname[index].last, pname[index].first);
		putchar(‘\n‘);
	}

}

int mycomp(const void *p1, const void *p2)
{
	const struct names * a1 = (const struct names *)p1;
	const struct names * a2 = (const struct names *)p2;

	int i = strcmp(a1->last, a2->last);
	if (i != 0)
		return i;
	else
		return strcmp(a1->last, a2->last);
}


7.下面是使用了可变函数的程序片断:

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
void show_array(const double ar[], int n);
double * new_d_array(int n, ...);
int main()
{
	double * p1;
	double * p2;

	p1 = new_d_array(5, 1.2, 2.3, 3.4, 4.5, 5.6);
	p2 = new_d_array(4, 100.0, 20.00, 8.08, -1890.0);
	show_array(p1, 5);
	show_array(p2, 4);
	free(p1);
	free(p2);

	return 0;
}

new_d_array()函数接受一个int参数和数量可变的double参数。该函数返回一个指向malloc()分配的内存块的指针。int参数指定动态数组中的元素个数:double值用于初始化元素(第一个值赋予第一个元素,依些类推)。提供show_array()和new_d_array()代码,使程序完整。

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>	//此题关键是stdarg.h与函数可变参数的运用
void show_array(const double ar[], int n);
double * new_d_array(int n, ...);
int main()
{
	double * p1;
	double * p2;

	p1 = new_d_array(5, 1.2, 2.3, 3.4, 4.5, 5.6);
	p2 = new_d_array(4, 100.0, 20.00, 8.08, -1890.0);
	show_array(p1, 5);
	show_array(p2, 4);
	free(p1);
	free(p2);

	return 0;
}

double * new_d_array(int lim, ...)
{
	va_list va;
	va_start(va, lim);
	double * p;
	p = (double *)malloc(lim * sizeof(double));
	for (int i = 0; i < lim; i++)
		p[i] = va_arg(va, double);
	va_end(va);

	return  p;
}

void show_array(const double ar[], int n)
{
	int i;
	for (i = 0; i < n; i++)
		printf("%.2lf ", ar[i]);
	printf("\n");
}


本文出自 “30岁学编程” 博客,请务必保留此出处http://xiongyi85.blog.51cto.com/8756903/1661356

C Primer Plus (第五版) 第十六章 C预处理器和C库 编程练习

标签:c primer plus   (第五版   ) 第十六章   编程练习   c预处理器和c库   

原文地址:http://xiongyi85.blog.51cto.com/8756903/1661356

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!