南哪2022-5-function
题单介绍
大家好啊,这里是某CQ!
这次是第一次准时推出的C-PL dotOJ补完计划!
其实这章题目还是挺水的,老师貌似是有选择性的听取了上次开会的提议,让OJ的前几题较为简单,便于练习。
这章主要是要求我们通过函数将代码分块,各个函数解决小范围内的一些问题,然后将它们组合起来解决整个问题。
如果你并没有学习函数并能灵活使用,那么这次的OJ作业对你来说仍然十分煎熬磨人。
那么,函数究竟是干嘛用的呢?
来看下面一个例子
```c
int n;
int cycle(int x)
{
if (x > n)
x -= n;
if (x < 1)
x += n;
return x;
}
int main()
{
while (1)
x = cycle(x + 1)
return 0;
}
```
(这代码当然是个死循环,不要想着去运行)
(某CQ将这个函数用在了约瑟夫问题当中,他发现这玩意真的很好用。)
通过写这样一个cycle函数,我们将x的值成功的限制在了1到n的范围内,使得x可以在某一范围内循环地往右运动。
你实际上可以发现函数只不过是把一些东西放到另一个地方去写罢了。这有什么用呢?
非也!当你在很多地方都要做同一种操作,你就堆在主函数里面?那自然写出来的代码是十分臃肿的。
想想不久前你可能仍然挣扎在数百行代码之中,但你会发现你实际上大部分的代码都是在复制粘贴。
如果有一种代码能够统一的表示这些操作,那该多好啊?
这就是函数的用途所在,把一些繁复的语句打包,在你想用的时候,说一声就完事了。
我们来分析一下函数的定义方法:
首先,函数是不能定义在某一个函数里面的,我们一直在写的int main()就是一个特殊的函数,每一份C语言代码都必须要运行它。
我们以上面的cycle函数为例,来解释一下函数的结构:
首先是这个函数的返回值类型:我们在cycle函数中需要获得x限制在1到n范围内的值,所以它的返回值肯定是我们想要得到的那个值,也就是一个int值。
然后是这个函数的名字,这个不必说,函数后面一定有括号,括号中可以填一些传入该函数的参数,说人话,就是告诉函数它需要知道这些值,它才能给你算出答案来。在cycle函数中我们传入了经过处理的x值,希望通过函数将它限制在1到n的范围内。
另外,如果你想要传入多个参数,你必须用逗号隔开并分别指定每一个变量的类型,即使变量类型是一样的也不行。
最后是这个函数的主体部分,具体怎么实现自然不必说,大家应该都会。
特别的,函数有一种特别的类型,叫做void函数,void函数没有返回值,而仅仅是作为一个操作存在,在主函数中可以直接调用这个函数来实现这个操作。
这也是某CQ一直想让你们把关键的变量放在主函数外面的原因。当你将函数定义在这些变量后面的时候,因为这些变量已经声明,在函数中没有变量与之重名的情况下(注意!这个非常的重要!),你可以调用和修改这些变量!
举一个void函数的例子:
```c
int a[10005]
void reverse(int l, int r)
{
while (l < r)
{
int t = a[l];
a[l] = a[r];
a[r] = t;
++l, --r;
}
}
```
通过这样一个函数,我们便实现了一个简单的操作:将数组从l到r这个区间反转。
(这也正是某CQ在这周的E题 下一个排列中用到的函数)
在函数的使用过程中,我们需要特别注意这一点:
当一个函数有了返回值,这个函数就会直接结束。
比如说大家可能已经尝试通过在主函数里直接return 0;来提前结束主函数,这也是一个优化的小技巧,当你的函数已经得出结论,没必要继续下去的时候,你能直接通过返回值来立即离开这个已经没有用的函数。
可能你想问,void函数也能返回值吗?
当然可以啊,void只要返回空的不就行了嘛,也就是说,在void函数中,你也可以使用return;来直接退出。
这样就大致讲解了函数的使用方法。
还不明白?来告诉你们一个使用实例:
本周作业D题,也就是确定进制那道题,你可以编写一个判断是否确认符合进制规则的函数,再编写一个将n进制的数转化为10进制的数的函数,然后判断pqr是否在某一个进制下符合条件?只需要在这三个数都符合条件的情况下,转化为十进制的p和q的乘积等于十进制下的r就行了哦
是不是感觉比不用函数的思路简单许多?
(某CQ表示函数真的很好用,大家一定要多加练习)
这次的题单也许会出现之前题单中出现的题目,某CQ这次希望大家使用函数的方法来解决这些题目。
感谢各位的收看!