1、假设变量x和n是两个正整数,我们知道x/n这个表达式的结果是取Floor(取下限),
例如x是17,n是4,则结果是4。如果希望结果取Ceiling(取上限)应该怎么写表达式呢?
例如x是17,n是4,则结果是5,而x是16,n是4,则结果是4。
#include <stdio.h>
int ceiling(int a, int b)
{
int tmp = 0;
tmp = a / b;
if (a % b > 0)
{
tmp += 1;
}
return tmp;
}
int flooring(int a, int b)
{
return (int)(a / b);
}
int main(int argc, char *argv[])
{
printf("%d\n", ceiling(7, 3));
printf("%d\n", flooring(7, 3));
return 0;
}
2、递归求解n的阶乘。
#include <stdio.h>
unsigned int factorial(unsigned int n)
{
if (0 == n)
{
return 1;
}
return n * factorial(n - 1);
}
int main(int argc, char *argv[])
{
printf("0! = %u\n", factorial(0));
printf("3! = %u\n", factorial(3));
printf("5! = %u\n", factorial(5));
printf("6! = %u\n", factorial(6));
return 0;
}
3、编写递归函数求两个正整数a和b的最大公约数(GCD,Greatest Common Divisor),
使用Euclid算法:
1. 如果a除以b能整除,则最大公约数是b。
2. 否则,最大公约数等于b和a%b的最大公约数。
Euclid算法是很容易证明的,请读者自己证明一下为什么这么算就能算出最大公约数。
#include <stdio.h>
int max_common_divisor(int a, int b)
{
if (0 == a % b)
{
return b;
}
else
{
return max_common_divisor(b, a % b);
}
}
int main(int argc, char *argv[])
{
printf("%d\n", max_common_divisor(6, 18));
printf("%d\n", max_common_divisor(13, 18));
printf("%d\n", max_common_divisor(36, 18));
printf("%d\n", max_common_divisor(9, 6));
return 0;
}
4、编写程序数一下1到100的所有整数中出现多少次数字9。在写程序之前先把这些问题考虑清楚:
1. 这个问题中的循环变量是什么?
2. 这个问题中的累加器是什么?用加法还是用乘法累积?
3. 取一个整数的个位和十位在第 2 节 “if/else语句”的练习中已经练过了,这两个表达
式应该怎样用在程序中?
#include <stdio.h>
int calc_num(void)
{
int i = 0;
int decade_bit = 0;
int unit_bit = 0;
int cnt = 0;
for (i = 1; i < 100; i++)
{
decade_bit = i / 10;
unit_bit = i % 10;
if (9 == decade_bit)
{
cnt++;
}
if (9 == unit_bit)
{
cnt++;
}
}
return cnt;
}
int main(int argc, char *argv[])
{
printf("%d\n", calc_num());
return 0;
}
5、编写程序打印乘法口诀表。
#include <stdio.h>
void print_multi_table(void)
{
int i = 0;
int j = 0;
for (i = 1; i < 10; i++)
{
for (j = 1; j <= i; j++)
{
printf("%d * %d = %d ",j, i, j*i);
}
printf("\n");
}
}
int main(int argc, char *argv[])
{
print_multi_table();
return 0;
}
6、编写程序打印菱形。
#include <stdio.h>
#include <stdlib.h>
void print_rhombus(int n)
{
int i = 0;
int j = 0;
for (i = 1; i < 2*n; i++)
{
for (j = 1; j < 2*n; j++)
{
if (abs(i - n) + abs(j - n) < n)
{
printf("*");
}
else
{
printf(" ");
}
}
printf("\n");
}
}
int main(int argc, char *argv[])
{
print_rhombus(5);
print_rhombus(9);
return 0;
}
7、编写程序使cpu占用率为%100 %50 和波形呈正弦波形
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <math.h>
#include <sys/time.h>
/*波形周期,单位ms*/
#define WAVE_T 10*1000
/*采样次数*/
#define SAMPLE_CNT 10000
/*采样间隔,单位us*/
#define SAMPLE_GAP 1*1000
/*圆周率PI*/
#define PI 3.14
void cpu_usage_100(void)
{
while (1);
}
void cpu_usage_50(void)
{
struct timeval time;/*{{{*/
long long start_t = 0;
long long end_t = 0;
while (1)
{
gettimeofday(&time, NULL);
start_t = time.tv_sec * 1000000 + time.tv_usec;
end_t = start_t;
while (end_t - start_t < 60000)
{
gettimeofday(&time, NULL);
end_t = time.tv_sec * 1000000 + time.tv_usec;
}
usleep(60000);
}/*}}}*/
}
void cpu_usage_sine(void)
{
struct timeval time;
long long start_t = 0;
long long end_t = 0;
long long busy_t[SAMPLE_CNT];
long long idle_t[SAMPLE_CNT];
int i = 0;
for (i = 0; i < SAMPLE_CNT; i++)
{
busy_t[i] = SAMPLE_GAP * 0.5 * (1 + sin(2 * PI / SAMPLE_CNT * i));
idle_t[i] = SAMPLE_GAP - busy_t[i];
//printf(" busy_t[%d] = %lld\n", i, busy_t[i]);
//printf(" idle_t[%d] = %lld\n", i, idle_t[i]);
}
i = 0;
while (1)
{
gettimeofday(&time, NULL);
start_t = time.tv_sec * 1000000 + time.tv_usec;
end_t = start_t;
while (end_t - start_t < busy_t[i])
{
gettimeofday(&time, NULL);
end_t = time.tv_sec * 1000000 + time.tv_usec;
}
usleep(idle_t[i]);
i = (i+1) % SAMPLE_CNT;
}
}
int main(int argc, char *argv[])
{
//cpu_usage_100();
//cpu_usage_50();
cpu_usage_sine();
return 0;
}
8、设计一个函数返回一个数组指针。
#include <stdio.h>
int swap(int *a, int *b)
{
if (*a == *b)
{
return 0;
}
*a = *a ^ *b;
*b = *a ^ *b;
*a = *a ^ *b;
return 0;
}
int (*fun(void))[3]
{
static int a[3] = {1, 7, 5};
return &a;
}
int main(int argc, char *argv[])
{
int (*p)[3] = NULL;
int i = 0;
int j = 0;
p = fun();
for (i = 0; i < 3; i++)
{
printf("%d\n", (*p)[i]);
}
for (i = 0; i < 3; i++)
{
for (j = 0; j < 3; j++)
{
if ((*p)[j] <= (*p)[j+1])
{
swap(&(*p)[j], &(*p)[j+1]);
}
}
}
for (i = 0; i < 3; i++)
{
printf("%d\n", (*p)[i]);
}
return 0;
}
9、将下面的代码,只改变一个字符输出10个*。
#include <stdio.h>
int main(int argc, char **argv)
{
int cnt = 10;
int i = 0;
for (i = 0; i < cnt; i--)
{
printf("*");
}
return 0;
}
1、 for (i = 0; -i < cnt; i--)
{
printf("*");
}
2、 for (i = 0; i < cnt; cnt--)
{
printf("*");
}
3、 for (i = 0; i + cnt; i--)
{
printf("*");
}
10、不使用if for switch while ? : 语句,也不使用* / 运算符,求1+2+3+… +100?
#include <stdio.h>
int calc_sum(int a)
{
static int sum = 0;
sum += a;
(a--) && calc_sum(a);
return sum;
}
int main(int argc, char *argv[])
{
printf("%d\n", calc_sum(100));
return 0;
}