a.
#define FPM 5280 /*每英里的英尺数*/
dist = FPM * miles;
b.
#define FEET 4
#define POD FEET + FEET
plort = FEET * POD;
c.
#define SIX = 6;
nex = SIX;
d.
#define NEW(X) X + 5
y = NEW(y);
berg = NEW(berg) * lob;
est = NEW(berg) / NEW(y);
nilp = lob * NEW(-berg);
答:
a.
有效。dist = 5280 * miles
b.
有效。plort = 4 * 4 + 4
c.
无效。
d.
有效。y = y + 5
有效,但可能有误。est = berg + 5 * lob
有效,但可能有误。est = breg + 5 / y + 5
有效(传递进去的是负值不是一个符号加变量)。 lob * (-berg) + 5
答:
#define NEW(X) ((X) + 5)//尽可能地多使用括号将宏函数的变量括起
#define MIN(X, Y) ((X) > (Y) ? (Y) : (X))
#define EVEN_GT(X, Y) ((X) % 2 == 0 && (X) > (Y) ? 1 : 0)
例如,若参数为3 + 4和4 * 12,则打印:
3 + 4 is 7 and 4 * 12 is 48
答:
#define SHOW(X, Y) printf(#X " is %d and " #Y " is %d\n", X, Y)
a.创建一个值为25的命名常量。
b.SPACE表示空格字符。
c.PS()代表打印空格字符。
d.BIG(X)代表X的值加3。
e.SUMSQ(X, Y)代表X和Y的平方和。
答:
a. #define SIZE 25
b. #define SPACE ’ ’
c. #define PS() printf(" ")
d. #define BIG(X) ((X) += 3)
e. #define SUMSQ(X,Y) ((X)(X)+(Y)(Y))
name: fop; value: 23; address: ff464016
答:
#define SHOW(X) printf(“name:”#X";value:%d;address:%p", X, &X)
#define DROP//如果不需要跳过代码,则删除该指令
#ifndef DROP
/*被跳过的代码块*/
#endif
#ifdef PR_DATE
printf("%s\n", _ _DATE_ _);
#endif
第一个正常返回一个double类型的数,输入1.3时,返回值为1.69。
第二个在返回之前将结果强制转化为了int型,丢失精度。在返回转换时,返回值的小数部分全为0,输入1.3时,程序中返回值为1
第三个也在返回之前也将结果强制转化为int型,但在强制转化前结果加上了0.5,当输入为1.3时,返回值为2,输入为1.2时,返回值为1,以此来判断是调用了哪一个函数
答:
#define BOOL(X) _Generic((X), _Bool : "boolean", default : "not boolean")
#include
int main(int argc, char argv[])
{
printf("The square root of %f is %f\n", argv[1],sqrt(argv[1]) );
}
答:
argv[] 应该改为 *argv[]
第一个%f应该改为%s
第二个argv[1]应当使用类似于atof()的函数转换为float型
应当在头文件中加上math.h
程序在使用sqrt应该排除参数是负数
a.如何正确调用qsort()?
b.如何正确定义comp()?
答:
a.
qsort((void*)scores, (size_t)1000, sizeof(int), comp);
b.
int comp(const void *a, const void *b)
{
return (*(int*)a) - (*(int*)b);
}
a.编写memcpy()的函数调用,把data2中的前100个元素拷贝到data1中。
b.编写memcpy()的函数调用,把data2中的后100个元素拷贝到data1中。
答:
a. memcpy(data1, data2, 100 * sizeof(double));
b. memcpy(data1, data2 + 200, 100 * sizeof(double));
代码:
#ifndef DRAFT_ALLDEFINE_H
#define DRAFT_ALLDEFINE_H
#include
#include
#include
#include
#include
#include
#define MAX(X, Y) ((X) > (Y) ? (X) : (Y))
#define MIN(X, Y) ((X) > (Y) ? (Y) : (X))
#endif // !DRAFT_ALLDEFINE_H
两数的调和平均数这样计算:先得到两数的倒数,然后计算两个倒数的平均值,最后取计算结果的倒数。使用#define指令定义一个宏“函数”,执行该运算。编写一个简单的程序测试该宏。
代码:
#include
#include
#define HARMONIC_MEAN(X, Y) 2 / (1 / (X) + 1 / (Y))
int main()
{
float a, b;
printf("Please give me two numbers, and I'will calculate the harmonic mean: ");
scanf("%f %f", &a, &b);
printf("The harmonic mean of %.2f and %.2f is %.2f.\n", a, b, HARMONIC_MEAN(a, b));
system("pause");
return 0;
}
运行结果:
极坐标用向量的模(即向量的长度)和向量相对x轴逆时针旋转的角度来描述该向量。直角坐标用向量的x轴和y轴的坐标来描述该向量(见图16.3)。编写一个程序,读取向量的模和角度(单位:度),然后显示x轴和y轴的坐标。相关方程如下:
x = r*cos A
y = r*sin A
需要一个函数来完成转换,该函数接受一个包含极坐标的结构,并返回一个包含直角坐标的结构(或返回指向该结构的指针)。
代码:
#include
#include
#include
#define PI 3.1415926
struct Rectangular translate(struct Polar p);
void show_polar(const struct Polar p);
void show_rectangular(const struct Rectangular r);
struct Polar // 极坐标
{
float r;
float A;
};
struct Rectangular // 直角坐标
{
float x;
float y;
};
int main()
{
struct Polar polar;
struct Rectangular rec;
printf("please input the length and angle of the vector:\n");
scanf("%f %f", &polar.r, &polar.A);
show_polar(polar);
rec = translate(polar);
show_rectangular(rec);
system("pause");
return 0;
}
struct Rectangular translate(struct Polar p)
{
struct Rectangular r;
r.x = p.r * cos(p.A * PI / 180.0);
r.y = p.r * sin(p.A * PI / 180.0);
return r;
}
void show_polar(const struct Polar p)
{
printf("length: %.2f, angle: %.2f°\n", p.r, p.A);
}
void show_rectangular(const struct Rectangular r)
{
printf("x: %.2f, y: %.2f\n", r.x, r.y);
}
运行结果:
ANSI库这样描述clock()函数的特性:
#include
clock_t clock (void);
这里,clock_t是定义在time.h中的类型。该函数返回处理器时间,其单位取决于实现(如果处理器时间不可用或无法表示,该函数将返回-1)。然而,CLOCKS_PER_SEC(也定义在time.h中)是每秒处理器时间单位的数量。因此,两个 clock()返回值的差值除以 CLOCKS_PER_SEC得到两次调用之间经过的秒数。在进行除法运算之前,把值的类型强制转换成double类型,可以将时间精确到小数点以后。编写一个函数,接受一个double类型的参数表示时间延迟数,然后在这段时间运行一个循环。编写一个简单的程序测试该函数。
代码:
#include
#include
#include
void delay(double a);
int main()
{
double a;
printf("Enter a number of seconds(q to quit): ");
while (scanf("%lf", &a) == 1)
{
delay(a);
printf("Enter a number of seconds(q to quit): ");
}
printf("Bye!\n");
system("pause");
return 0;
}
void delay(double a)
{
double s = (double)clock();
double f = 0;
while ((a - f) > 0.00000001)
{
f = ((double)clock() - s) / CLOCKS_PER_SEC;
}
printf("%.2lfs have passed.\n", f);
}
运行结果:
编写一个函数接受这些参数:内含int类型元素的数组名、数组的大小和一个代表选取次数的值。该函数从数组中随机选择指定数量的元素,并打印它们。每个元素只能选择一次(模拟抽奖数字或挑选陪审团成员)。另外,如果你的实现有time()(第12章讨论过)或类似的函数,可在srand()中使用这个函数的输出来初始化随机数生成器rand()。编写一个简单的程序测试该函数。
代码:
#include
#include
#include
#define LEN 10
void Print_sd(int *, int, int);
int Find_df(int *, int);
int main()
{
srand(time(0));
int data[LEN] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
int count;
printf("Enter a number, I'll pick you randomly(enter q to quit):\n");
while (scanf("%d", &count) && count <= 10)
{
// printf("%d", count);
Print_sd(data, LEN, count);
}
printf("Bye!\n");
system("pause");
return 0;
}
void Print_sd(int *ar, int n, int count)
{
int index[LEN] = {0};
int i = 0;
printf("The result of random selection: ");
while (i < count)
{
index[i] = Find_df(index, n);
// printf("%d ", index[i]);
printf("%d ", ar[index[i] - 1]);
i++;
}
printf("\n");
}
int Find_df(int *index, int n)
{
int key = rand() % 10 + 1;
// printf("%d", key);
for (int i = 0; i < n; i++)
if (key == index[i]) // 如果找到相同的下标,就向下递归
{
key = Find_df(index, n);
break;
}
return key;
}
运行结果:
修改程序清单16.17,使用struct names元素(在程序清单16.17后面的讨论中定义过),而不是double类型的数组。使用较少的元素,并用选定的名字显式初始化数组。
代码:
#include
#include
#include
#include
#define NUM 100
#define LEN 40
struct Name
{
char first[LEN];
char last[LEN];
};
struct Name staff[NUM];
void fillarray(struct Name ar[], int n);
void showarray(const struct Name ar[], int n);
int mycomp(const void *p1, const void *p2);
int main()
{
fillarray(staff, NUM);
puts("Random list:");
showarray(staff, NUM);
qsort((void *)staff, (size_t)NUM, sizeof(struct Name), mycomp);
puts("\nSorted list:");
showarray(staff, NUM);
system("pause");
return 0;
}
void fillarray(struct Name ar[], int n)
{
srand((unsigned long)time(0));
for (int i = 0; i < n; i++)
{
int firstLen = rand() % 10 + 1;
int lastLen = rand() % 10 + 1;
// 随机生成first
for (int j = 0; j < firstLen; j++)
{
ar[i].first[j] = rand() % 26 + 'a';
}
// 随机生成last
for (int j = 0; j < lastLen; j++)
{
ar[i].last[j] = rand() % 26 + 'a';
}
}
}
void showarray(const struct Name ar[], int n)
{
int i;
for (i = 0; i < n; i++)
{
printf("%10s.%-10s ", ar[i].first, ar[i].last);
if (i % 4 == 3)
putchar('\n');
}
if (i % 4 != 0)
putchar('\n');
}
int mycomp(const void *p1, const void *p2)
{
const struct Name *ps1 = (const struct Name *)p1;
const struct Name *ps2 = (const struct Name *)p2;
int res = strcmp(ps1->last, ps2->last);
if (res != 0)
return res;
else
return strcmp(ps1->first, ps2->first);
}
运行结果:
C:\Users\81228\Documents\Program\VScode C Program\chapter16>16.6
Random list:
zljeezddl.in cwytt.hdtagwq xmeukcamly.vjkgkkii npuh.hrhvis
caxadvqb.lf asf.puhpvvd ldidgum.g lctizmdm.rnr
ipdafwiv.bcaofo vvabbuqylv.bm rdipz.soahbrqg ovnnzv.g
kpjekesh.jhzmnmwh dpzmepdnw.enkmhjz cqoemj.nbojoonr mcqm.clqauva
csqr.ovlmxyuamf jiyp.mlnhp zmadux.stszk ycohuah.qpy
gie.dgg tfgglmtcb.ozcmibpkpa uwcfxxcm.hvujzr bovtp.xrmyadnd
enqnrlz.jkzmxbsi ntxnyw.uhpum uobllmhluj.ixwhn zshca.lsuokfu
osqrvl.ccilrqfl svcennyfwx.zzyycfiix uqwoxrh.v og.hzssx
rdswg.k joktr.edm pttefhmm.ki mi.cip
mhielxt.qdjzixk rvchhwiyy.gj nvsui.zreupwvm qgvrutmbao.z
itoeq.jrnoxil z.fnlq eyoyblsp.jxqoaupbfo eysgmne.egcezy
upumzuhb.i xwbgj.s lq.pl cy.baqbirsxx
i.kwr foktbczo.gi qvfqh.pcg avwnrye.xjpg
jzfe.z bznxq.gfcqkvhbp w.agmzauzcml vbswqcdook.thxhrruanf
xtcqq.trxnctf qxgok.iefpavd ixym.vgyviq ryv.rcurez
kashj.vlf hpertiqynm.pk unsoezl.ioqph mzmmxiao.wzmwluvk
bbnr.mihjc gtgvz.iccmltrru xfu.qc fv.dzbk
trixyn.idcat vu.oyjielzi isnt.yagoiaity qkydpctgw.ngppmnkex
ymhafpltrz.ziyifn q.c epbanewzmw.jd rbetyax.ujpqpliz
fwvjhpterm.th zzxli.agikkic nlooufyt.pp d.hkyye
tgxt.vffv ubsbanlok.kpoxdgp tmicu.q l.l
xxwez.ozqd myxzsgwjyg.bbwygsi ktqrvbmt.ro sssuf.xx
s.agmdsk wlpo.bipdjysce q.mb mvemkw.dbyh
jvestub.aqi plwttjy.dy sn.answyswc qpbht.kxlm
w.nwdvd ifa.cjeqsvfat qqesohik.bn thdydiqblr.elyas
Sorted list:
zzxli.agikkic s.agmdsk w.agmzauzcml sn.answyswc
jvestub.aqi cy.baqbirsxx myxzsgwjyg.bbwygsi ipdafwiv.bcaofo
wlpo.bipdjysce vvabbuqylv.bm qqesohik.bn q.c
osqrvl.ccilrqfl mi.cip ifa.cjeqsvfat mcqm.clqauva
mvemkw.dbyh gie.dgg plwttjy.dy fv.dzbk
joktr.edm eysgmne.egcezy thdydiqblr.elyas dpzmepdnw.enkmhjz
z.fnlq ldidgum.g ovnnzv.g bznxq.gfcqkvhbp
foktbczo.gi rvchhwiyy.gj cwytt.hdtagwq d.hkyye
npuh.hrhvis uwcfxxcm.hvujzr og.hzssx upumzuhb.i
gtgvz.iccmltrru trixyn.idcat qxgok.iefpavd zljeezddl.in
unsoezl.ioqph uobllmhluj.ixwhn epbanewzmw.jd kpjekesh.jhzmnmwh
enqnrlz.jkzmxbsi itoeq.jrnoxil eyoyblsp.jxqoaupbfo rdswg.k
pttefhmm.ki ubsbanlok.kpoxdgp i.kwr qpbht.kxlm
l.l caxadvqb.lf zshca.lsuokfu q.mb
bbnr.mihjc jiyp.mlnhp cqoemj.nbojoonr qkydpctgw.ngppmnkex
w.nwdvd csqr.ovlmxyuamf vu.oyjielzi tfgglmtcb.ozcmibpkpa
xxwez.ozqd qvfqh.pcg hpertiqynm.pk lq.pl
nlooufyt.pp asf.puhpvvd tmicu.q xfu.qc
mhielxt.qdjzixk ycohuah.qpy ryv.rcurez lctizmdm.rnr
ktqrvbmt.ro xwbgj.s rdipz.soahbrqg zmadux.stszk
fwvjhpterm.th vbswqcdook.thxhrruanf xtcqq.trxnctf ntxnyw.uhpum
rbetyax.ujpqpliz uqwoxrh.v tgxt.vffv ixym.vgyviq
xmeukcamly.vjkgkkii kashj.vlf mzmmxiao.wzmwluvk avwnrye.xjpg
bovtp.xrmyadnd sssuf.xx isnt.yagoiaity jzfe.z
qgvrutmbao.z ymhafpltrz.ziyifn nvsui.zreupwvm svcennyfwx.zzyycfiix
请按任意键继续. . .
C:\Users\81228\Documents\Program\VScode C Program\chapter16>
下面是使用变参函数的一个程序段:
#include
#include
#include
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类型的值用于初始化元素(第1个值赋给第1个元素,以此类推)。编写show_array()和new_d_array()函数的代码,完成这个程序。
代码:
#include
#include
#include
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);
system("pause");
return 0;
}
void show_array(const double ar[], int n)
{
for (int i = 0; i < n; ++i)
{
printf("%.2lf ", ar[i]);
}
printf("\n");
}
double *new_d_array(int n, ...)
{
va_list ap; // 声明一个对象储存参数
va_start(ap, n); // 把ap初始化为参数列表
double *array = (double *)malloc(n * sizeof(double));
for (int i = 0; i < n; i++)
array[i] = va_arg(ap, double); // 访问参数列表中的每一项
va_end(ap);
return array;
}
运行结果: