Jack's Blog

流淌的心,怎能阻拦,吹来的风,又怎能阻挡。

C语言学习五

Jacob posted @ Apr 08, 2017 10:30:47 AM in C语言 with tags C语言 哈工大 小白进阶,sse , 1116 阅读

今天早上又刷了一早上的题

本周练习为啥还有18个???

我表示极大的纳闷。。。

难度较低的题已经被我刷光了,可能难题刷的比较慢吧。

仅存的慰藉是我已经刷到了1810分,今天加加油,看能不能全刷完上2000分(要求全部的18道题都做对),但我感觉压力山大!!!

 

向着2500分的目标迈进;

如果可能,争取刷到3000分,拿到3分的加分!

废话不多说了!上代码!!!


PART .1

1.用递归方法编程计算输出Fibonacci数列,同时打印出计算Fibonacci数列每一项时所需的递归调用次数。
**输入格式要求:"%d" 提示信息:"Input n:"
**输出格式要求:"Fib(%d)=%d, count=%d\n"
程序运行示例如下:
Input n:10
Fib(1)=1, count=1
Fib(2)=1, count=3
Fib(3)=2, count=5
Fib(4)=3, count=9
Fib(5)=5, count=15
Fib(6)=8, count=25
Fib(7)=13, count=41
Fib(8)=21, count=67
Fib(9)=34, count=109
Fib(10)=55, count=177

 

先上我的垃圾错误代码

 

#include<stdio.h>
fib(a);
extern int c=0;
main()
{
    printf("Input n:");
    int n,i,c;
    scanf("%d",&n);
    fib(n);
}
fib(a)
{
    c=0;
    if(a==1)
    {
        printf("Fib(%d)=%d, count=%d\n",a,1,1);
        return 1;
    }
    if(a==2)
    {
        printf("Fib(%d)=%d, count=%d\n",a,2,3);
        return 1;
    }
    else
    {
    c++;
    printf("Fib(%d)=%d, count=%d\n",a,fib(a-1)+fib(a-2),c);
    }
}

其实这道题的计算原理都不难,很轻松的就想出来了。

难的地方就在与输出格式还有c的计算。(吐槽一下——格式真的好烦人)

懒得查答案了,反正金币一大堆,不如直接花10金币看答案

#include <stdio.h>
long Fib(int a);
int count;     /*全局变量count用于累计递归函数被调用的次数,自动初始化为0*/
int main()
{                        
    int n, i, x;
    printf("Input n:");
    scanf("%d", &n);
    for (i = 1; i <= n; i++)
    {                        
        count = 0;   /* 计算下一项Fibonacci数列时将计数器count清零 */
        x = Fib(i);
        printf("Fib(%d)=%d, count=%d\n", i, x, count);
    }
    return 0;
}                        
/* 函数功能:用递归法计算Fibonacci数列中的第n项的值 */
long Fib(int n)
{                        
    long f;
    count++;      /* 累计递归函数被调用的次数,记录于全局变量count中 */
    if (n == 0)   f = 0;
    else if (n == 1)   f = 1;
    else   f = Fib(n - 1) + Fib(n - 2);
    return f;
}                 
 

PART .2

编写函数在return 值的时候,笔者总是希望return 多个值。

然而C语言不允许;

询问Kai大佬后大佬说用Struct   然而小白还没学到结构体怎么办???

于是便想到了下面的一些方法(参考链接):

1.利用全局变量


  分析:全局变量作为C语言的一个知识点,虽然我们都了解它的特点,但在实际教学过程中应用得并不是很多。由于全局变量的作用域是从定义变量开始直到程序结束,而对于编写有多个返回值的C语言函数,我们可以考虑把要返回的多个值定义成全局变量。当函数被调用时,全局变量被更改,我们再把更改后的全局变量值应用于主调函数中。函数被调用后被更改后的全局变量值即为函数的数个返回值。下面以一个实例演示该方法的应用。
  实例1:编写函数求3个数中的最大值与最小值。
  方法:把最大值、最小值分别定义成2个全局变量max、min,在用户自定义函数中把求出来的最大值与最小值分别赋给全局变量max、min。函数调用完毕后全局变量的max、min值即保存了函数要求返回的值。程序参考代码如下:

  #include "stdio.h"
  #include "conio.h"
  int max,min;/*定义两个全局变量用于保存函数返回值*/
  void max_min(int a,int b,int c) /*定义求最大最小值的函数*/
  {max=min=a; /*初始化最大最小值*/
   if(max   if(max   if(min>b)min=b;
  if(min>c)min=c;
  }
  main()
  {int x,y,z;
  printf(" 请输入3个整数:\n");
  scanf("%d,%d,%d",&x,&y,&z);
  max_min(x,y,z) ;/*调用求最大值与最小值的函数*/
  printf("三个数中的最大值为:%d;最小值为:%d",max,min);/*输出最大值与最小值*/
  getch();
  }         

  调试结果如下:

  请输入3个整数:
  5,-6,2
  三个数中的最大值为:5;最小值为:-6


  注意:该方法虽然可以实现有多个返回值的函数,但由于全局变量不能保证值的正确性(因为其作用域是全局,所以程序范围内都可以修改它的值,如果出现错误将非常难以发现),并且全局变量增加了程序间模块的耦合,所以该方法要慎用。


2.传递数组指针
  
  分析:在教学过程中,我们知道C语言函数参数的传递方式有值传递与地址传递。当进行值传递时,主调函数把实参的值复制给形参,形参获得从主调函数传递过来的值运行函数。在值传递过程中被调函数参数值的更改不能导致实参值的更改。而如果是地址传递,由于传递过程中从实参传递过来的是地址,所以被调函数中形参值的更改会直接导致实参值的更改。因此,我们可以考虑把多个返回值作为数组元素定义成一个数组的形式,并使该数组的地址作为函数的形式参数,以传址方式传递数组参数。函数被调用后,形参数组元素改变导致实参改变,我们再从改变后的实参数组元素中获得函数的多个返回值。以下实例演示该方法的应用。
  实例2:编写函数求一维整形数组的最大值与最小值,并把最大值与最小值返回给主调函数。
  方法:以指针方式传递该一维数组的地址,然后把数组的最大值与数组的第一个元素交换,把数组的最小值与最后一个元素交换。函数被调用完毕后,实参数组中的第一元素为数组的最大值,实参数组中最后一个元素为数组的最小值,从而实现返回数组的最大值与最小值的功能。程序参考代码如下:

  #include "stdio.h"
  #include "conio.h"
  void max_min(int *ptr,int n) /*定义求数组最大值最小值的函数,传递数组指针*/
  {int i,j,k;/*j保存最大值所在位置,k保存最小值所在位置*/
  int *temp;/*用于交换位置*/
  *temp=*ptr;
  for(i=0;i  {
  if(*ptr<*(ptr+i))/*最大值与第一个元素进行交换*/
  {
  k=i;
  *temp=*ptr;
  *ptr=*(ptr+k);
  *(ptr+k)=*temp ;
  }
  if(*(ptr+n-1)>*(ptr+i))/*最小值与最后一个元素进行交换*/
  {
  j=i;
  *temp =*(ptr+n-1);
  *(ptr+n-1)=*(ptr+j);
  *(ptr+j)= *temp ;}
  }
  }
  /*调用最大最小值函数*/
  main()
  {
  int A[6],i;
  for(i=0;i<6;i++)
   scanf("%d",&A[i]);
  max_min(A,6);
  printf("max=%d, min=%d\n \n",A[0],A[5]);
  getch();
  }


  调试结果如下:
  请输入6个整形数,以空格隔开:
  5 8 9 32 -6 4
  max=32,min=-6

注意:该方法适用于多个返回值的数据类型一致的情况。当返回值数据类型不一致时,不适用该方法。
  
3.传递结构体指针
  
  分析:结构体作为教学中的一个难点,教材对它介绍的内容并不多,应用的实例更是少之又少,所以学生对于结构体普遍掌握情况不理想。其实,编写返回多个值的C语言函数,也可以考虑采用结构体的方式去实现。通过方法2,我们知道如果返回的数个数值的数据类型不一致,可以通过定义全局变量实现有多个返回值的C语言函数,也可以考虑把要求返回的数个值定义成一个结构体,然后同样以传递结构体指针方式把结构体的指针传递给形参结构体指针,那么函数中对形参结构体的修改即是对实参结构体的修改,函数被调用后获取的实参结构体成员即为函数的多个返回值,下面以实例演示该方法的应用。
  实例3:编写一个用户自定义函数,允许用户录入学生的基本信息(包括学号、姓名、所属班级、总评成绩),并返回这些基本信息给主调函数。
  
  方法:把学生基本信息定义成一个结构体,在用户自定义函数中传递该结构体的指针,则自定义函数中对结构体成员的录入操作即是对实参结构体成员的录入操作,从而实现多个返回值。参考代码如下:

  #include "stdio.h"
  #include "conio.h"
  struct inf{/*定义学生结构体,分别包含成员学号、姓名、班别、总评成绩*/
   char xh[12];
   char name[20];
   char class[15];
   int chj;
  };
  main(void)
  {
  struct inf a1; /*定义学生结构体类型变量*/
  void xxxx(struct inf *ptr);
  printf("请输入学号,姓名,班别,总评成绩,以空格隔开:\n") ;
  xxxx(&a1);/*调用函数,以学生结构体类型变量地址作为实参*/
  printf("学号:%s,姓名: %s,班别:%s,总评成绩:%d",a1.xh, a1.name,a1.class,a1.chj);
  getch();
  }
  void xxxx(struct inf *ptr)/*该函数实现对结构体成员数据的录入操作*/
  {
   char xh1[12],name1[20],class1[15];
   int chj1;
  scanf("%s%s%s%d",xh1,name1,class1,&chj1);
   strcpy(ptr->xh,xh1);
  strcpy(ptr->name,name1);
  strcpy(ptr->class,class1);
  ptr->chj=chj1;
   }


  调试结果如下:
  请输入学号,姓名,班别,总评成绩,以空格隔开:
  200102LiLi200185
  学号:200102,姓名: LiLi,班别:2001,总评成绩:85
  注意:当函数要求返回的多个值是相互联系的或者返回的多个值数据类型不一致时可以采用该方法。
  
4.结束语
  对于以上这三种方法,如果想要返回的数个值数据类型一致,可以考虑采用方法2;而对于不同数据类型的返回值,如果各个数值之间是相互联系的,则方法3较为合适;方法1虽然在很多情况下都可以实现多个返回值的C语言函数,但毕竟全局变量应用过程中有很多危险,要慎重使用。
  通过对以上几种方法的分析讲解,在教学过程中,学生再遇到这样的问题时,就能根据返回值的情况选择合适的途径去实现多个返回值的C语言函数。另外,如果再遇到类似的无法用教材知识点去直接解决的问题时,他们基本都能举一反三地尝试采用间接方式去解决。

Avatar_small
Junior Dakil Result 说:
2022年9月02日 21:44

Madrasah Education Board is most popular in the country of Bangladesh, and they have successfully conducted the Junior Dakhil Certificate examination tests for Grade 8 level students at all education boards at all divisions in district wise across in the country, and there are lakhs of students are appeared from all Madhrasah’s of the country, and the Secondary Education Board also completed the JDC terminal exams 2022 successfully based on JDC routine 2022. Junior Dakil Result madrasah Board The Class 8th Grade student who has appeared to the annual final terminal exams they are waiting to check JDC Result 2022 Madrasah Board with full mark sheet, the student who is qualified in this examination they are promoted to higher class in Mass education board, every student who has appeared to the JDC exams 2022 are waiting to check their result with subject wise marks along with final GPA grade point.


登录 *


loading captcha image...
(输入验证码)
or Ctrl+Enter