算法学习之函数

函数与递归
简单函数的编写
如果函数在执行的过程中碰到了return语句,将直接退出这个函数,不去执行后面的语句。
题一:组合数
输入非负整数n和m,输出组合数Cmn=n!/m!(n-m)!,其中m<=n<=20。
分析:题目中的公式出现了多次n!,把它作为一个函数编写时比较合理的。
#include <conio.h>
#include<stdio.h>
#include<string.h>
int f(int n){
    int i,m = 1;
    for(i = 1;i<=n;i++){
          m *= i;
    }
    return m;
}
int main(){
    int m,n;
    scanf("%d%d",&m,&n);
    printf("%d\n",f(n)/(f(m)*f(n-m)));
    getch();
    return 0;
}

题二:孪生素数
如果n和n+2都是素数,则称它们是孪生素数。输入m,输出两个数均不超过m的最大孪生素数。
5<=m<=10000。
分析:
素数,指在一个大于0的自然数中,除了1和此整数自身外,不能被其他自然数整除的数。1不是素数。
#include <conio.h>
#include<stdio.h>
#include<string.h>
int is_prime(int x)
{
    int i;
    for(i = 2;i*i<=x;i++){
         if(x%i == 0)return 0;//及时退出,性能
    }
    return 1;
}
int main(){
    int i,m;
    scanf("%d",&m);
    for(i = m-2;i>=3;i--){
          if(is_prime(i)&&is_prime(i+2)){
            printf("%d %d\n",i,i+2);
            break;
          }
    }
    getch();
    return 0;
}

写子函数,是门学问,要写的有质量。这样下次使用时,才会更好用。

地址和指针
#include <conio.h>
#include<stdio.h>
#include<string.h>
void swap(int a,int b){
     int t=a;a=b;b=t;
}
int main(){
    int a = 3,b=4;
    swap(3,4);
    printf("%d %d\n",a,b);
    getch();
    return 0;
}
结果并没有交换成功,函数处理之后,只在函数中的变量有效。
main中的是实参,swap中的是形式参数。
用指针实现变量交换。
#include <conio.h>
#include<stdio.h>
#include<string.h>
void swap(int* a,int* b){
     int t=*a;*a=*b;*b=t;
}
int main(){
    int a = 3,b=4;
    swap(&a,&b);
    printf("%d %d\n",a,b);
    getch();
    return 0;
}
这样就有效果了
*a是指a指向的变量,而不仅是a指向的变量所拥有的值。
*a = *a + 1就是让a指向的变量自增1。

递归
阶乘f(n) = n!
f(0) = 1;
f(n) = f(n-1)*n  (n>=1)
对应的程序为

#include <conio.h>
#include<stdio.h>
#include<string.h>
int f(int n)
{
    return n == 0?1:f(n-1)*n;
}
int main(){
    printf("%d\n",f(4));
    getch();
    return 0;
}
自己调用自己就是递归,但是要有一个出口,让程序走出递归。

在C语言中,调用自己和调用其他函数并没有任何本质区别,都是建立新栈帧。
打个比如
皇帝(拥有main函数的栈帧):大臣,你给我算一下f(3)。
大臣(拥有f(3)的栈帧):知府,你给我算一下f(2)。
知府(拥有f(2)的栈帧):县令,你给我算一下f(1)。
县令(拥有f(1)的栈帧):师爷,你给我算一下f(0)。
师爷(拥有f(0)的栈帧):回老爷,f(0)=1。
县令:会知府大人,f(1)=1。
知府:回大人,f(2)=2。
大臣:回皇上 ,f(3)= 6。

posted @ 2013-09-01 20:29  TBHacker  阅读(508)  评论(0编辑  收藏  举报