C_Primer_Plus编程练习答案(个人练习仅供参考)

第二章

第三章

第四章

第五章

1. 编写一个程序, 把用分钟表示的时间转换成用小时和分钟表示的时间。 使用 #define 或 const 创建一个表示 60 的符号常量或 const 变量。 通过 while 循环让用户重复输入值, 直到用户输入小于或等于 0 的值才停止循环。

//通过scanf返回值读取用户输入
#include <stdio.h>

#define MIN_TO_HOUR 60

int main(void)
{
    int mins, hours, last_mins;

    puts("Enter the time (minute) you want to transfer (<= 0 to quit):");
    while (scanf("%d", &mins) == 1 && mins > 0)
    {
        hours = mins / MIN_TO_HOUR;
        last_mins = mins % MIN_TO_HOUR;
        printf("%d minutes equal to %d hour(s) and %d minute(s).\n", mins, hours, last_mins);

        puts("Enter the time (minute) you want to transfer (<= 0 to quit):");
    }
    puts("Bye!");

    return 0;
}

2. 编写一个程序, 提示用户输入一个整数, 然后打印从该数到比该数大 10 的所有整数( 例如, 用户输入 5, 则打印 5~15 的所有整数, 包括 5 和 15)。 要求打印的各值之间用一个空格、 制表符或换行符分开。

//通过for循环打印即可
#include <stdio.h>

#define LEN 10

int main(void)
{
    int n;

    puts("Enter an integer:");
    scanf("%d", &n);

    for (int i = n; i <= n + LEN; i++)
        printf("%d ", i);
        
    return 0;
}

3. 编写一个程序, 提示用户输入天数, 然后将其转换成周数和天数。 例如, 用户输入 18, 则转换成 2周 4 天。 以下面的格式显示结果:
18 days are 2 weeks, 4 days.

//整数的取模 % 和除法 / 
#include <stdio.h>

#define D_TO_W 7

int main(void)
{
    int days;

    puts("Enter the number of days you want to convert (negative or zero to quit):");
    while(scanf("%d", &days) == 1 && days > 0)
    {
        printf("%d days are %d weeks, %d days.\n", days, days / D_TO_W, days % D_TO_W);
        puts("Enter the number of days you want to convert (negative or zero to quit):");
    }
    puts("Bye!");

    return 0;
}

4. 编写一个程序, 提示用户输入一个身高( 单位: 厘米), 并分别以厘米和英尺、 英寸为单位显示该值,允许有小数部分。 程序应该能让用户重复输入身高, 直到用户输入一个非正值。 其输出示例如下:

Enter a height in centimeters: 182
182.0 cm = 5 feet, 11.7 inches
Enter a height in centimeters (<=0 to quit): 168.7
168.7 cm = 5 feet, 6.4 inches
Enter a height in centimeters (<=0 to quit): 0
bye

//1英尺 = 30.48厘米,1英寸 = 2.54厘米
#include <stdio.h>

#define CM_TO_FEET 30.48
#define CM_TO_INCH 2.54

int main(void)
{
    double height, inches;
    int feet;

    printf("Enter a height in centimeters: ");
    while(scanf("%lf", &height) == 1 && height > 0)
    {
        feet = height / CM_TO_FEET;
        inches = (height - feet * CM_TO_FEET) / CM_TO_INCH;
        
        printf("%.1f cm = %d feet, %.1f inches\n", height, feet, inches);
        printf("Enter a height in centimeters (<= to quit): ");
    }
    puts("Bye");

    return 0;
}

5. 修改程序 addeirmp.c (程序清单 5.13 ), 你可以认为 addemup.c 是计算 20 天里赚多少钱的程序
( 假设第 1 天赚$1 、 第 2 天赚S2、 第 3 天赚S3, 以此类推)。 修改程序, 使其可以与用户交互, 根据用户输入的数进行计算( 即, 用读入的一个变量来代替 20)。

//for循环即可
#include <stdio.h>

int main(void)
{
    int n;
    int sum, count;

    puts("Enter a integer:");
    scanf("%d", &n);

    for (count = 1; count <= n; count++)
        sum += count; 
    printf("sum = %d", sum);

    return 0;
}

6. 修改编程练习 5 的程序, 使其能计算整数的平方和( 可以认为第 1 天赚$1、 第 2 天赚$4、 第 3 天赚$9,以此类推, 这看起来很不错)。 C 没有平方函数, 但是可以用 n * n 来表示 n 的平方
 

//for循环即可
#include <stdio.h>

int main(void)
{
    int n;
    int sum, count;

    puts("Enter a integer:");
    scanf("%d", &n);

    for (count = 1; count <= n; count++)
        sum += count * count; 
    printf("sum = %d", sum);

    return 0;
}

7. 编写一个程序, 提示用户输入一个 double 类型的数, 并打印该数的立方值。 自己设计一个函数计算并打印立方值。 main() 函数要把用户输入的值传递给该函数。

//设计函数,该函数为void类型,接受double类型的参数
#include <stdio.h>

void cube(double num);

int main(void)
{
    double num;

    printf("Enter a number to calculate its cube: ");
    scanf("%lf", &num);
    cube(num);

    puts("\nBye");
    return 0;
}

void cube(double num)
{
    double ncube = num * num * num;

    printf("%.2f cubed is %.2f\n", num, ncube);
}

8. 编写一个程序, 显示求模运算的结果。 把用户输入的第 1 个整数作为求模运算符的第 2 个运算对象,该数在运算过程中保持不变。 用户后面输入的数是第 1 个运算对象。 当用户输入一个非正值时, 程序结束。 其输出示例如下:
This program computes moduli.
Enter an integer to serve as the second operand: 256
Now enter the first operand: 438
438 % 256 is 182
Enter next number for first operand (<= 0 to quit): 1234567
1234567 % 256 is 135
Enter next number for first operand (<= 0 to quit): 0
Done

//注意取模仅用于整数
#include <stdio.h>

int main(void)
{
    int dividend, divisor;

    puts("This program computes moduli.");
    printf("Enter an integer to serve as the second operand: ");
    scanf("%d", &divisor);
    printf("Now enter the first operand: ");
    while (scanf("%d", &dividend) == 1 && dividend > 0)
    {
        printf("%d %% %d is %d\n", dividend, divisor, dividend % divisor);

        printf("Enter next number for first operand (0 <= to quit): ");
    }
    puts("Done");

    return 0;
}

9. 编写一个程序, 要求用户输入一个华氏温度。 程序应读取 double 类型的值作为温度值, 并把该值作为参数传递给一个用户自定义的函数 Temperatures()。 该函数计算摄氏温度和开氏温度, 并以小数点后面两位数字的精度显示 3 种温度。 要使用不同的温标来表示这 3 个温度值。 下面是华氏温度转摄氏温度的公式:
摄氏温度 = 5.0 / 9.0 * (华氏溫度 - 32.0)
开氏温标常用于科学研究, 0 表示绝对零, 代表最低的温度。 下面是摄氏温度转开氏温度的公式:
开氏溫度 = 摄氏溫度 + 273.16
Temperatures ( ) 函数中用 const 创建温度转换中使用的变量。 在 main ( ) 函数中使用一个循环让用户重复输入温度, 当用户输入 q 或其他非数字时, 循环结束。 scanf() 函数返回读取数据的数量, 所以如果读取数字则返回 1, 如果读取 q 则不返回 1。可以使用=运算符将 scanf ( ) 的返回值和 1 作比较, 测试两值是否相等。

// 1.摄氏温度(centigrade) = 5.0 / 9.0 * (华氏溫度(Fahrenheit) - 32.0)
// 2.开氏溫度(Kelvin) = 摄氏溫度 + 273.16
// 3.自定义函数Tempertatures(),接受double类型华氏温度进行转换,返回类型为void。

#include <stdio.h>

void Temperatures(double Fah);

int main(void)
{
    double Fah;

    puts("The program performs temperature conversion.");
    puts("Now enter the Fahrenheit temperature: ");
    while (scanf("%lf", &Fah) == 1)
    {
        Temperatures(Fah);

        puts("Now enter next Fahrenheit temperature (q to quit): ");
    }
    puts("Done");

    return 0;
}

void Temperatures(double fah)
{
    const double cen = 5.0 / 9.0 * (fah - 32);
    const double kel = cen + 273.16;

    printf("Fahrenheit temperature: %.2f\n", fah);
    printf("Centigrade temperature: %.2f\n", cen);
    printf("    Kelvin temperature: %.2f\n", kel);
}

第六章

1. 编写一个程序, 创建一个包含 26 个元素的数组, 并在其中存储 26 个小写字母。 然后打印数组的所有内容。
// 循环赋值打印

#include <stdio.h>

#define LEN 26

int main(void)
{
    int i;
    char arr[LEN];

    for (i = 0; i < LEN; i++)
    {
       arr[i] = (int)'a' + i;
       printf("%c ", arr[i]);
    }
    putchar('\n');

    return 0;
}

2. 使用嵌套循环, 按下面的格式打印字符:
$
$$
$$$
$$$$
$$$$$
 

// 嵌套循环
#include <stdio.h>

#define sign '$'

int main(void)
{
    int i, j;
    int n = 5;

    for (i = 1; i <= n; i++)
    {   
        for (j = 0; j < i; j++)
            printf("%c", sign);
        putchar('\n');
    }

    return 0;
}

3. 使用嵌套循环, 按下面的格式打印字母:
F
FE
FED
FEDC
FEDCB
FEDCBA
注意: 如果你的系统不使用 ASCII 或其他以数字顺序编码的代码, 可以把字符数组初始化为字母表中的字母:

char lets[27] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";

然后用数组下标选择单独的字母, 例如 lets[0]是 'A', 等等。
 

#include <stdio.h>

#define ROWS 6

int main(void)
{
    int row;
    char ch;

    for (row = 0; row < ROWS; row++)
    {
        for (ch = 'F'; ch >= ('F' - row); ch--)
            printf("%c", ch);
        putchar('\n');
    }

    return 0;
}

4. 使用嵌套循环, 按下面的格式打印字母:
A
BC
DEF
GHIJ
KLMNO
PQRSTU

如果你的系统不使用以数字顺序编码的代码, 请参照练习 3 的方案解决。
 

#include <stdio.h>

#define ROWS 6

int main(void)
{
    int row, col;
    char ch = 'A';

    for (row = 0; row < ROWS; row++)
    {
        for (col = 0; col <= row; col++, ch++)
            printf("%c", ch);
        putchar('\n');
    }

    return 0;
}

5. 编写一个程序, 提示用户输入大写字母。 使用嵌套循环以下面金字塔型的格式打印字母:
A
ABA
ABCBA
ABCDCBA
ABCDEDCBA
打印这样的图形, 要根据用户输入的字母来决定。 例如, 上面的图形是在用户输入 E 后的打印结果。
提示: 用外层循环处理行, 每行使用 3 个内层循环, 分别处理空格、 以升序打印字母、 以降序打印字母。

如果系统不使用 ASCII 或其他以数字顺序编码的代码, 请参照练习 3 的解决方案。
 

#include <stdio.h>

#define space ' '

int main(void)
{
    char ch;
    int row;

    printf("Enter a capital letter: ");
    scanf("%c", &ch);

    int i, j;
    row = ch - 'A' + 1; //计算行数
    
    for (i = 0; i < row; i++)
    {
        //打印空格
        for (j = row - i - 1; j > 0; j--)   
            printf("%c", space);
        //升序打印
        for (ch = 'A'; ch <= 'A' + i; ch++)
            printf("%c", ch);
        //降序打印
        for (ch = ch - 2; ch >= 'A'; ch--)
            printf("%c", ch);
        putchar('\n');
    }

    return 0;
}

6. 编写一个程序打印一个表格, 每一行打印一个整数、 该数的平方、 该数的立方。 要求用户输入表格的上下限。 使用一个 for 循环。
 

#include <stdio.h>

int main(void)
{
    long up_limit, lo_limit;
    long n;

    printf("The program prints the trivial and cubic of all integers in a given range.\n");
    printf("Now enter the upper limit: ");
    scanf("%d", &up_limit);
    printf("Next, enter the lower limit: ");
    scanf("%d", &lo_limit);

    printf("number    square    cube\n");
    for (n = lo_limit; n <= up_limit; n++)
        printf("%4ld     %5ld     %5ld\n", n, n * n, n * n * n);

    return 0;
}

7. 编写一个程序把一个单词读入一个字符数组中, 然后倒序打印这个单词。 提示: strlenO 函数( 第 4 章介绍过) 可用于计算数组最后一个字符的下标。
 

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

#define LEN 40

int main(void)
{
    int count;
    char words[LEN];

    printf("Enter a word: ");
    scanf("%s", words);

    count = strlen(words);

    for (int i = count - 1; i >= 0; i--)
        printf("%c", words[i]);
    
    return 0;
}

8. 编写一个程序, 要求用户输入两个浮点数, 并打印两数之差除以两数乘积的结果。 在用户输入非数字之前, 程序应循环处理用户输入的每对值。
 

//while循环输入,输入非数字退出循环

#include <stdio.h>

int main(void)
{
    float f1, f2;

    printf("Enter the first float: ");
    while (scanf("%f", &f1) == 1)
    {
        printf("Now enter the second float: ");
        if (scanf("%f", &f2) == 1)
            printf("(%.2f - %.2f) / (%.2f * %.2f) = %.4f\n", f1, f2, f1, f2, (f1 - f2) / (f1 * f2));
        else
            break;
        printf("Enter the first float (q to quit): ");
    }

    return 0;
}

9. 修改练习 8, 使用一个函数返回计算的结果。
 

#include <stdio.h>

float calculate(float a, float b);

int main(void)
{
    float f1, f2;

    printf("Enter the first float: ");
    while (scanf("%f", &f1) == 1)
    {
        printf("Now enter the second float: ");
        if (scanf("%f", &f2) == 1)
            printf("(%.2f - %.2f) / (%.2f * %.2f) = %.4f\n", f1, f2, f1, f2, calculate(f1, f2));
        else
            break;
        printf("Enter the first float (q to quit): ");
    }

    return 0;
}

float calculate(float a, float b)
{
    return ((a - b) / (a * b));
}

10. 编写一个程序, 要求用户输入一个上限整数和一个下限整数, 计算从上限到下限范围内所有整数的平方和, 并显示计算结果。 然后程序继续提示用户输入上限和下限整数, 并显示结果, 直到用户输入的上限整数等于或小于下限整数为止。 程序的运行示例如下:
Enter lower and upper integer limits: 5 9
The sums of the squares from 25 to 81 is 255
Enter next set of limits: 3 25
The sums of the squares from 9 to 625 is 5520
Enter next set of limits: 5 5
Done
 

// while循环处理输入

#include <stdio.h>

int main(void)
{
    unsigned long long lower, upper;
    unsigned long long sum;

    printf("Enter lower and upper integer limits: ");

    while ((scanf("%llu %llu", &lower, &upper) == 2) && upper > lower)
    {
        while (getchar() != '\n')
            continue;

        unsigned long long i;
        for (i = lower, sum = 0; i <= upper; i++)
            sum += i * i;
        printf("The sums of the squares from %llu to %llu is %llu\n", lower * lower, upper * upper, sum);
        
        printf("Enter next set of limits: ");
    }

    return 0;
}

11. 编写一个程序, 在数组中读入 8 个整数, 然后按倒序打印这 8 个整数。
 

// for循环读入,然后循环打印

#include <stdio.h>

#define SIZE 8

int main(void)
{
    int arr[SIZE];
    int i;

    for (i = 0; i < SIZE; i++)
        scanf("%d", &arr[i]);
    
    for (i = SIZE - 1; i >= 0 ; i--)
        printf("%d ", arr[i]);
    
    return 0;
}

12. 考虑下面两个无限序列:
1.0 + 1.0/2.0 + 1.0/3.0 + 1.0/4.0 + ...
1.0 -  1.0/2.0 + 1.0/3.0 -  1.0/4.0 + ...
编写一个程序计算这两个无限序列的总和, 直到到达某次数。 提示: 奇数个-1 相乘得-1, 偶数个-1 相乘得 1。 让用户交互地输入指定的次数, 当用户输入 0 或负值时结束输入。 查看运行 100 项、1000 项、 10000 项后的总和, 是否发现每个序列都收敛于某值?
 

//第一个序列为调和级数,不收敛
//第二个序列为交错调和级数,收敛于ln(2)
//两序列之和发散
#include <stdio.h>

int main(void)
{
    double sum1, sum2, sum;
    int n;
    double i;

    printf("Enter specified times (<= 0 to quit): ");
    while (scanf("%d", &n) == 1 && n > 0)
    {
        for (i = 1.0, sum1 = 0.0, sum2 = 0.0, sum = 0.0; i <= (double)n; i = i + 1.0)
        {
            //第一个序列和
            sum1 = sum1 + 1.0 / i;

            //第二个序列和
            if ((int)i % 2 == 1)
                sum2 = sum2 + 1.0 / i;
            else 
                sum2 = sum2 - 1.0 / i;

            //两个序列之和
            if ((int)i % 2 == 1)
                sum = sum + 2 * 1.0 / i;
        }
        printf("sum1 = %lf\nsum2 = %lf\n sum = %lf\n", sum1, sum2, sum);
        printf("Enter specified times (<= 0 to quit): ");
    }
    printf("Done");

    return 0;
}

13. 编写一个程序, 创建一个包含 8 个元素的 int 类型数组, 分别把数组元素设置为 2 的前 8 次幂。使用 for 循环设置数组元素的值, 使用 do while 循环显示数组元素的值。
 

#include <stdio.h>

#define SIZE 8

int main(void)
{
    int arr[SIZE];
    int i;
    arr[0] = 2;

    for (i = 1; i < SIZE; i++)
        arr[i] = arr[i-1] * 2;

    i = 0;
    do
    {
        printf("arr[%d] = %d\n",i, arr[i]);
        i++;
    } while (i < SIZE);

    return 0;  
}

14. 编写一个程序, 创建两个包含 8 个元素的 double 类型数组, 使用循环提示用户为第一个数组输入8 个值。 第二个数组元素的值设置为第一个数组对应元素的累积之和。 例如, 第二个数组的第 4个元素的值是第一个数组前 4 个元素之和, 第二个数组的第 5 个元素的值是第一个数组前 5 个元素之和( 用嵌套循环可以完成, 但是利用第二个数组的第 5 个元素是第二个数组的第 4 个元素与第一个数组的第 5 个元素之和, 只用一个循环就能完成任务, 不需要使用嵌套循环)。 最后, 使用循环显示两个数组的内容, 第一个数组显示成一行, 第二个数组显示在第一个数组的下一行, 而且每个元素都与第一个数组各元素相对应。
 

//第二个数组求和不使用嵌套循环,即只用一个循环完成

#include <stdio.h>

#define SIZE 8

int main(void)
{
    int i;
    double arr[SIZE];
    double sum[SIZE];

    //第一个数组赋值
    printf("Enter the value: ");
    for (i = 0; i < SIZE; i++)
    {
        scanf("%lf", &arr[i]);
        printf("Enter the next value: ");
    }
    putchar('\n');

    //第二个数组求和
    sum[0] = arr[0];
    for (i = 1; i < SIZE; i++)
        sum[i] = sum[i-1] + arr[i];
    
    //显示
    printf("arr:");
    for (i = 0; i < SIZE; i++)
        printf("    %8.2lf ", arr[i]);
    putchar('\n');
    
    printf("sum:");
    for (i = 0; i < SIZE; i++)
        printf("    %8.2lf ", sum[i]);
    putchar('\n'); 
       
    return 0;
}

15. 编写一个程序, 读取一行输入, 然后把输入的内容倒序打印出来。 可以把输入存储在 char 类型的数组中, 假设每行字符不超过 255。 回忆一下,%c: 转换说明,scanf()函数一次只能从输入中读取一个字符, 而且在用户按下 Enter 键时 scanf()函数会生成一个换行字符( \n )。

#include <stdio.h>

#define SIZE 255

int main(void)
{
    char arr[SIZE];
    int i = 0;

    while (scanf("%c", &arr[i]) == 1 && arr[i] != '\n' && i < SIZE)
        i++;

    for (i--; i >= 0; i--)
        printf("%c", arr[i]);
    
    return 0;
}

16. Daphne 以 10%的单利息投资了 100 美元( 也就是说, 每年投资获利相当于原始投资的 10% ) 。Deirdre以 5%的复合利息投资了 100 美元( 也就是说, 利息是当前余额的 5%, 包含之前的利息)。 编写一个程序, 计算需要多少年 Deirdre 的投资额才会超过 Daphne, 并显示那时两人的投资额。
 

#include <stdio.h>

#define INITIAL_FUNDING 100

int main(void)
{
    double Dap = INITIAL_FUNDING, Dei = INITIAL_FUNDING;
    int year;

    for (year = 0; Dei <= Dap; year++)
    {
        Dap += INITIAL_FUNDING * 0.1;
        Dei += Dei * 0.05;
    }
    printf("Now it's been %d years, Dephic has $%lf, Deirdre has $%lf.\n", year, Dap, Dei);

    return 0;
}

17. Chuckle Lucky 贏得了 100 万美元( 税后), 他把奖金存入年利率 8%的账户。 在每年的最后一天,Chuckie 取出 10 万美元。 编写一个程序, 计算多少年后 Chuckie 会取完账户的钱?
 

//先计算利率再取钱

#include <stdio.h>

int main(void)
{
    double money = 100;
    int year;

    for (year = 1; money > 0; year++)
    {
        money += money * 0.08;
        money -= 10;
    }

    printf("In %d years, Chuckie will run out of money.", --year);

    return 0;
}

18. Rabnud 博士加入了一个社交圈。 起初他有 5 个朋友。 他注意到他的朋友数量以 "F面的方式增长。第 1 周少了1个朋友, 剩下的朋友数量翻倍: 第 2 周少了 2 个朋友, 剩下的朋友数量翻倍。 一般而言, 第 N 周少了 N 个朋友, 剩下的朋友数量翻倍。 编写一个程序, 计算并显示 Rabnud 博士每周的朋友数量。 该程序一直运行, 直到超过邓巴数( Dunbar's number )邓巴数是粗略估算一个人在社交圈中有稳定关系的成员的最大值, 该值大约是 150。
 

#include <stdio.h>

#define DUNBAR 150

int main(void)
{
    int friends = 5;
    int week;

    for (week = 1; friends < DUNBAR; week++)
    {
        friends -= week;
        friends *= 2;

        printf("week = %d, friends = %d\n", week, friends);
    }

    return 0;
}

内容概要:本文档《opencv高频面试题.docx》涵盖了OpenCV的基础概念、图像处理操作、特征提取与匹配、目标检测与机器学习、实际编程题、性能优化以及进阶问题。首先介绍了OpenCV作为开源计算机视觉库,支持图像/视频处理、目标检测、机器学习等领域,应用于安防、自动驾驶、医学影像、AR/VR等方面。接着详细讲述了图像的存储格式(如Mat类)、通道的概念及其转换方法。在图像处理部分,讲解了图像灰度化、二值化、边缘检测等技术。特征提取方面,对比了Harris和Shi-Tomasi角点检测算法,以及SIFT、SURF、ORB的特征提取原理和优缺点。目标检测部分介绍了Haar级联检测原理,并阐述了如何调用深度学习模型进行目标检测。文档还提供了几个实际编程题示例,如读取并显示图像、图像旋转、绘制矩形框并保存等。最后,探讨了性能优化的方法,如使用cv2.UMat(GPU加速)、减少循环等,以及相机标定、光流等进阶问题。 适合人群:对计算机视觉有一定兴趣,具备一定编程基础的学习者或从业者。 使用场景及目标:①帮助学习者掌握OpenCV的基本概念和技术;②为面试准备提供参考;③为实际项目开发提供技术指导。 阅读建议:由于内容涵盖广泛,建议读者根据自身需求有选择地深入学习相关章节,并结合实际编程练习加深理解。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

ssssYYYssss

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值