【暑期每日一练】 day9

目录

选择题

(1)

解析: 

(2)

解析:

(3)

解析: 

(4)

解析: 

(5)

解析: 

编程题

题一

描述

示例

提示 

解析 

代码实现

题二

描述

示例

提示

解析

代码实现

总结

 


 

选择题

(1)

1、下列程序的输出是( )

#include<stdio.h>
int main()
{
    int a [12]= {1,2,3,4,5,6,7,8,9,10,11,12},*p[4],i;
    for(i=0;i<4;i++)
        p[i]=&a [i*3];
    printf("%d\n",p[3][2]);
    return 0;
}

A: 上述程序有错误  B: 6  C: 8  D: 12
答案: D

解析: 

p是一个指针数组,p[i] = &a[i*3]相当于是把数组a每3个一组分开并把每组的首地址存在p数组,此时p类似一个4行3列的二维数组,p[3][2]就是4行第3个元素12

(2)

2、二维数组X按行顺序存储,其中每个元素占1个存储单元。若 X[4][4] 的存储地址为 Oxf8b82140 , X[9][9] 的存储地址为 Oxf8b8221c ,则 X[7][7] 的存储地址为( )

A: Oxf8b821c4 B: Oxf8b821a6 C: Oxf8b82198 D: Oxf8b821c0
答案:A

解析:

假设每行有n个元素:那x[9][9]元素的地址 - x[4][4]元素的地址 = 0x21c-0x140=5n+5(21c和140是地址末三位的十六进制数),这里n是43,假设x[7][7]的地址是z,x[7][7]元素的地址 - x[4][4]元素的地址 = z-0x140 = 3n+3,z = 3n+3+140 =3*43+3+0x140 = 0x84+0x140 = 0x1c4,看地址的尾数,选择A

(3)

3、以下哪个选项可以正确描述 sizeof(double) ( )

A: 一个整型表达式 B: 一个双精度型表达式 C: 一个不合法的表达式 D: 一种函数调用
答案:A

解析: 

sizeof是C语言中的一个操作符,不是函数调用,简单的说其作用就是返回一个对象或者类型所占的内存字节数,结果是无符号整数,因此可以把它看作是整型表达式。所以选择A

(4)

4、下列代码运行后的结果是什么( )

int main()
{
    char a = 'a',b;
    printf("%c,", ++a);
    printf("%c\n", b = a++);
    return 0;
}

A: b,b  B: b,c  C: a,b  D: a,c
 答案:A

解析: 

变量a里边存的是字符'a',第一次输出先加加再输出,输出的是'b';第二次输出的时候,a先赋值再加加,赋值给b的就是a原来的值,输出b的时候的还是'b'

(5)

5、以下逗号表达式的值为( )

(x= 4 * 5 , x * 5) , x + 5;

A: 25  B: 20  C: 100  D: 45
 答案:A

解析: 

逗号表达式是从前到后依次计算子表达式,而其结果是最后一项的值,此题去掉括号后的表达式,和原表达式是等价的,先计算4*5并赋值给x,x变为20,中间x*5并没有改变x的值,最后一项x+5值是25,也就是整个表达式的值

编程题

题一

描述

自除数 是指可以被它包含的每一位数整除的数。

例如,128 是一个 自除数 ,因为 128 % 1 == 0,128 % 2 == 0,128 % 8 == 0。
自除数 不允许包含 0 。

给定两个整数 left 和 right ,返回一个列表,列表的元素是范围 [left, right] 内所有的 自除数 。

示例

eebf95bb786d4e349d612894931392b5.png

提示 

f1581e6a0f724730963db7e22f5ac897.png

解析 

自除数的判断,数字的每一位都能被源数字整除,有了这个规则,咱们只需要循环获取一个数字的每一位,然后与源数字取模判断是否为 0 ,如果中间有任意一次不为 0 ,则表示不是自除数。

接下来,只需要遍历数组中的每个元素,判断是否是自除数即可,如果是则加入到返回数组中。

代码实现

int* selfDividingNumbers(int left, int right, int* returnSize)
{
    int *ret = (int *)calloc(1000, sizeof(int));//动态申请足够大的空间用于存放返回的自除数
    *returnSize = 0;
    for (int i = left; i <= right; i++) 
    {
        int num = i;
        while(num)
        {
            int remainder = num % 10;//计算余数
            if (remainder == 0 || (i % remainder) != 0) 
            {//判断i自身与余数取模是否为0
            break;
            } 
            num /= 10;
        } 
    //如果num==0表示通过了每一位数的取模判断,则i就是自除数
        if (num == 0) 
         ret[(*returnSize)++] = i;
    } 
return ret;
}

题二

描述

给你一个整数数组 nums,返回 数组 answer ,其中 answer[i] 等于 nums 中除 nums[i] 之外其余各元素的乘积 。

题目数据 保证 数组 nums之中任意元素的全部前缀元素和后缀的乘积都在  32 位 整数范围内。

请不要使用除法

示例

5e9b343e4b18430e819c4a6e2a6bff48.png 

提示

22143baf561843c4afbec7729c9f89d2.png 

解析

暴力不考虑其他的因素的话,将所有数据乘积起来,然后遍历数组除以当前位置数据即可。
更优解法:将乘积分为两次进行,第一次先将每个位置左边的数据乘积计算出来放到返回数组中,后边第二次循环

将对应位置右边的数据乘积计算出来与返回数组对应位置的左半边乘积相乘得到结果。

示例: 一个数组 int nums[] = {2, 3, 4}

1b78c5eb105540e588b06253e77aec6d.png

代码实现

int* productExceptSelf(int* nums, int numsSize, int* returnSize)
{
    int *ret = (int *)malloc(numsSize * sizeof(int));
    *returnSize = numsSize;
    int left = 1, right = 1;
    //第一次循环,将当前位置左边的数字乘积填入返回数组中
    for (int i = 0; i < numsSize; i++) 
    {
        ret[i] = left;// 1 nums[0] nums[0]*nums[1] num[0]*nums[1]*nums[2] ....
        left *= nums[i];
    }
    //第二次循环,对于返回数组的元素从后往前进行,每次乘以右边元素的乘积
    for (int i = numsSize - 1; i >= 0; i--) 
    {
        ret[i] *= right; //最后一个成绩不需要乘以最后元素,乘以1就行
        right *= nums[i]; //right变化:1 nums[end] nums[end]*nums[end-1] .....
    } 
    return ret;
}

总结

关于今日练习讲解到这儿,欢迎各位留言交流以及批评指正,如果文章对您有帮助或者觉得作者写的还不错可以点一下关注,点赞,收藏支持一下。


 

 

  • 29
    点赞
  • 25
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 26
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 26
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

遇事问春风乄

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

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

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

打赏作者

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

抵扣说明:

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

余额充值