C语言练习7讲解

可能因为课题的深入吧,我们的题目难度也与日俱增。今天关于数组的题目有些很值得讲的,今天和大家分享一下我的看法。

逆序

因为今天上午已经学过并且讲过,所以这题没啥好说的。
从0到n - 1输入数组,从n - 1到0输出数组。
两个for循环搞定。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <stdio.h>

int main(void)
{
int n;
scanf("%d",&n);
int array[11]; //1-10 略大一点,留有余地。
for(int i = 0;i < n;i++)
{
scanf("%d",&array[i]);
}
for(int i = n - 1;i > 0;i--)
{
printf("%4d",array[i]);
}
return 0;
}

数组最小值

审题得:题目的要求是求最小值以及其下标,然后输出下标最小的一个
最小值我们知道怎么求,一个for循环搞定。
其实因为你找到了第一个值,把它设置为最小值之后,
就算另一个值与它相等,我们找的是比它小的数,而不是相等,
相当于没关系了。

那么开写

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
#include <stdio.h>

int main(void)
{
int n, min, iPosit;
int array[1001]
scanf("%d",&n);

for(int i = 0;i < n;i++)
{
scanf("%d",&array[i]);
}
min = array[0];
for(int i = 1;i < n;i++)
{
if(min > array[i])
{
min = array[i];
iPosit = i;
}
}
printf("%d %d",min,iPosit);
return 0;
}

数组n个输入的模版-仅供参考。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#include <stdio.h>

int main(void)
{
int n;
int array[101]
scanf("%d",&n);

for(int i = 0;i < n;i++)
{
scanf("%d",&array[i]);
}
//...
return 0;
}

删除元素:

在直播中我们只讲函数,思路今天上午已经讲过了。

一个是PrintArr,相信不太用多说

1
2
3
4
5
6
7
void PrintArr(int a[], int n)
{
for(int i = 0;i < n;i++)
{
print("%d", a[i]);
}
}

另一个就是我们的del函数,用的是覆盖的思路。

1
2
3
4
5
6
7
void del(int a[], int n, int i)
{
for(int k = i;k < n - 1;k++)
{
a[k] = a[k + 1];
}
}

今天下午看到我们小伙伴有对调用时数组的形式不太理解的,
这里说一下。
我们调用函数的时候参数填入的是数组的名称
比如我们调用del函数时,我们是这样写的。

1
2
del(array, n, k);
//array为数组名,n为长度,k是要删除的下标。

不需要加中括号,那样的话指向的就是数组中的元素了。
比如array[10],甚至我们数组中没有这个元素,那样就会导致运行错误
余下就执行函数就好,注意PrintArr在覆盖之后输出n - 1的值。
因为数组在覆盖之后最后一个值与倒数第二个值是相等的。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
#include <stdio.h>

void del(int a[], int n, int i);
void PrintArr(int a[],int n);

int main(void)
{
int n, k;
int array[10];
scanf("%d", &n);

for(int i = 0;i < n;i++)
{
scanf("%d",&array[i]);
}

scanf("%d",&k);
del(array, n, k);
PrintArr(array, n - 1);
return 0;
}

void del(int a[], int n, int i)
{
for(int k = i;k < n - 1;k++)
{
a[k] = a[k + 1];
}
}

void PrintArr(int a[], int n)
{
for(int i = 0;i < n;i++)
{
printf("%d ", a[i]);
}
}

数组元素

下一题,加入一个find函数,在主函数中加入一个if判断找不找的到就好
找的到,返回i,找不到,返回-1.

[find函数]

1
2
3
4
5
6
7
8
int find(int a[], int n, int x)
{
for(int i = 0;i < n;i++)
{
if(x == a[i]) return i;
}
return -1;
}

后面判断一下find的值是不是大于0即可。

路旁的树

一条数轴,相当于一个一维数组。
维度这个概念其实是与数轴相关的。
如果平面直角坐标系的话一般就会用二维数组,
像天梯赛模拟题的炎爆那道题

思路是,首先把每个元素初始化成2
注意今天上午老师讲的那个错误,

1
int array[1001] = {2}

不要犯这种错误。
正确的是用for循环把n个元素的值赋为2

这题应该挺简单的。
也就是多次下把这个区间上的元素全部降为0
(注意不是-2,这样区间重叠就成负的了。)

然后再定义一个sum变量,再一个一个地加。
最后输出值即可。
代码如下。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#include <stdio.h>

int main(void)
{
int n, N, sum = 0, x, y;
int array[1001];
scanf("%d",&n);
scanf("%d",&N);

for(int i = 0;i < n;i++)
{
array[i] = 2;
}

for(int i = 0;i < N;i++)
{
scanf("%d %d",&x,&y);
for(int i = x - 1;i <= y - 1;i++)
{
array[i] = 0;
}
}
for(int i = 0;i < n;i++)
{
sum += array[i];
}
printf("%d",sum);
return 0;
}

按分数段统计学生人数

简单的循环题,但是被强行地转成了数组题。
如果输入的t在输入成绩之前这就是循环了,我们都比较擅长。
直接输入数据,然后用for循环一个一个比对,
造一个初始值为0的变量,然后如果大于等于那个值就加一。
最后输出就好。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#include <stdio.h>

int main(void)
{
int n, gradelimit, num = 0;
int array[101];
scanf("%d",&n);

for(int i = 0;i < n;i++)
{
scanf("%d",&array[i]);
}

scanf("%d",&gradelimit);
for(int i = 0;i < n;i++)
{
if(array[i] >= gradelimit) num += 1;
}
printf("%d",num);
return 0;
}

两道比较难的题目

1.区间元素和

这道题难在判断的条件多,
我在做的时候没有想到left与right小于0的情况,
所以没有做对,但是后来结合志鹏的解答也给出了简单点的答案。
但是不太好理解,你们要是觉得不好懂看志鹏的就好。
虽然用的是C++,你们看条件就好。

志鹏同学的答案
(std::cin就相当于我们的scanf,std::cout就相当于我们的printf)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include <stdio.h>

int main(void)
{
int n, left, right;
long long sum = 0;
int array[101];
scanf("%d",&n);

for(int i = 0;i < n;i++)
{
scanf("%d",&array[i]);
}

scanf("%d %d",&left, &right);
if(left < n)
{
for(int i = left;i <= right;i++)
{
if(i < n && i >= 0)
sum += array[i];
}
printf("%d",sum);
}
else printf("%lld",0);
return 0;
}

确保left是小于n的,那么两个集合就一定有交集。
然后保证加的是在0到n - 1上的元素(数组内的)。

找出旷课的人

先放代码,直播讲

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
#include <stdio.h>

void Sort(int a[], int n)
{
int t;
for(int i = 0;i < n - 1;i++)
{
for(int j = i;j < n;j++)
{
if(a[i] > a[j])
{
t = a[i];
a[i] = a[j];
a[j] = t;
}
}
}
}

int main(void)
{
int m, n, flag, count = 0, l = 0;
int array1[10001];
int array2[10001];
int array3[10001];
scanf("%d %d",&m, &n);

for(int i = 0;i < m;i++)
{
scanf("%d",&array1[i]);
}
for(int i = 0;i < n;i++)
{
scanf("%d",&array2[i]);
}

for(int i = 0;i < m;i++)
{
flag = 0;
for(int j = 0;j < n;j++)
{
if(array1[i] == array2[j])
{
flag = 1;
break;
}
}
if(flag == 0)
{
array3[l] = array1[i];
count += 1;
l++;
}
}

if(count == 0) printf("good\n");
else
{
Sort(array3, l);
for(int i = 0;i < l;i ++)
{
printf("%d ", array3[i]);
}
}
return 0;
}

一次模块化的实践,但我当时很怕时间超限。。
由几个部分组成
判断相等-加入数组-排序(冒泡)-输出。

宿舍的选择

很简单的一道题,关于long long,只是为了防止越界吧。
判断宿舍可住人数与目前的人数的差,然后与学长的人数相比就好。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#include <stdio.h>

int main(void)
{
int m,n,p,q;
long long count = 0;
scanf("%d",&m);
scanf("%d",&n);
for(int i = 0;i < m;i++)
{
scanf("%d %d",&p,&q);
if((q - p) > n)
count += 1;
}

printf("%d",count);
return 0;
}

最后说说,这几道题还是很好地帮助我们锻炼了循环那边的知识
也帮我们抓起来了现在刚学的数组,
通过写题也得到了一些数学模型上的思考,挺好的。

打赏
  • 版权声明: 本博客所有文章除特别声明外,著作权归作者所有。转载请注明出处!
  • Copyrights © 2023-2024 大学生暮暖
  • 访问人数: | 浏览次数:

请我喝杯奶茶吧~

支付宝
微信