zoukankan      html  css  js  c++  java
  • 2017-2018-1 20179226 《从问题到程序》第4周学习总结

    教材学习知识点总结

    • 某些特殊情况下,浮点数运算的误差积累更迅速:
      1.将一批较小的数值一个个加到很大的数上
      2.两个值很接近的数相减,可能导致结果的精度大幅度下降。
    • fabs是<math.h>里求浮点数的绝对值的标准库数学函数。
    • break语句只能用在循环语句以及switch语句里,作用是使当前循环语句立刻终止。
    • 用结束标志控制的循环:可以为使用者提供一个特殊“值”。
    • 函数调用scanf("%d",&x)只能产生三种不同函数值
      1.返回1表示成功读入一项数据。
      2.返回0表示读入数据失败。
      3.返回EOF值表示遇到了文件结束。
    • 标准库里把getchar的返回类型定义为int(而不是char)。
    • 如果是要求处理所有可以从键盘输入的字符,我们可以通过利用getchar的返回值和符号常量EOF。如果getchar执行时遇到文件结束,就返回EOF值。
    • 交互式程序:执行中不断从外界获取信息,有输入的程序都是交互式程序。
    • 要在程序里统计时间,程序头部就要写#include<time.h>,做程序计时通常用表达式:clock()/CLOCKS_PER_SEC
    • 从本质上区分,可以有两类基本的确定测试数据的方式:白箱测试和黑箱测试
      1.白箱测试:根据程序的内部结构确定测试数据。
      2.黑箱测试:根据程序所解决问题的要求去确定测试过程和数据,并不考虑程序内部如何解决问题。
    • 程序驱动(测试平台):为检查有用的程序或者程序部分而写的虚拟主函数。
    • 循环中的几种变量
      1.循环控制变量:for(n=0;n<10;++n)中的n。
      2.累计变量:sum += n中sum。
      3.递推变量:x1=x2; x2=x3; x3=...x1...x2...;中的x1,x2,x3。

    教材学习中的问题和解决过程

    • 问题1:“由于浮点数运算有误差,不能保证它一定得到所需的结果,所以人们一般不采用浮点数控制循环的次数。”浮点数运算有什么误差?
    • 问题1解决方案:书中通过乌龟旅行的例子说明了浮点数运算确实可能带来误差,但是我还是不太理解,查了资料http://blog.csdn.net/iloli/article/details/8447571之后发现,例如:
    float a = 0.65f;
    float b = 0.6f;
    float c = a - b;
    

    此时c为0.0499999523,而不是0.05。其根本原因是计算机所使用二进制01代码无法准确表示某些带小数位的十进制数据。
    我们知道是无法从根本上解决这个问题的,但我们可以有一些曲线救国的方法,下面列举几个:

    1. 因为二进制数值可以准确表示整数(可以使用整数转换为二进制方法验证下),所以可以将小数乘以10或100等变成整数,然后做整数运算,最后再通过除以10或100等获得结果。
    2. 通过截取结果的有效小数位数等,来取得最好的近似结果,然后在做处理。
    3. 对于可以用有限长度的二进制数值表示的十进制数值,可以使用存储位数大于其长度的数据类型。
    • 问题2:EOF值表示文件结束,什么是文件结束?
    • 问题2解决方案:书上很浅显的说“一般的C系统把EOF定义-1。它一定不是正数,因此不会与scanf的其他返回值混淆。”还是不太明白,查阅资料后知道EOF在系统里可以用CTRL+Z或CTRL+D来送入文件结束信息,其中在windows对应的按键是CTRL+Z键,在linux系统上对应的按键是CTRL+D。比如下面的代码:
    #include <stdio.h>
    int main()
    {
    int c;
    while ((c = getchar()) != EOF)
    putchar(c);
    return 0;
    }
    

    运行程序按CTRL+Z键,即会显示“^Z",再次按回车键即可退出程序。

    • 问题3:while(scanf("%lf",&x) != EOF)执行中不小心输入了字母m,这一程序为什么就会进入无穷循环?
    • 问题3解决方案:http://blog.csdn.net/wei_cheng18/article/details/71056413
      scanf("%lf",&x)从缓冲区接受数字,而当我们输入字母或其他时,字符就一直留在缓冲区,循环第二次时,scanf再次从缓冲区获取时,还是不是数字,就相当跳过了scanf这一句......从而,造成死循环。
      如何解决呢?
      1.在scanf这一句后面加一句getchar(); 用于接受字符;
      2.在scanf这一句前面加fflush(stdin); 这一函数用于清空缓冲区,但他并不适用于所有编译器,遇到vs2015,gcc编译器时,它就失效了。
  • 相关阅读:
    02-Java 数组和排序算法
    Spring Security 入门
    mysql外键理解
    redis能否对set数据的每个member设置过期时间
    Redis sortedset实现元素自动过期
    mysql之触发器trigger
    一篇很棒的 MySQL 触发器学习教程
    mysql触发器
    云游戏
    mysql触发器个人实战
  • 原文地址:https://www.cnblogs.com/9226ryf/p/7978626.html
Copyright © 2011-2022 走看看