「C 基础」编程习惯和窍门

Tips

  • 学习算法最好的方法并不是编写程序,而是手算
  • 千万不要图快——如果没有足够的时间来实践,那么学的快,忘的也快
  • 手工模拟的方法重点在于:记录每条语句执行之后各个变量的值
  • 黑盒测试:只考察解决问题的能力,而不关心采用了什么方法
  • 伪代码:在实际应用中并不太拘泥于伪代码的格式,主要目的是描述算法梗概,避开细节,启发思路
  • 尽量缩短变量的定义范围
  • 变量在未赋值前是不确定的,特别的,它不一定等于 0
  • Keep It Simple and Stupid 保持程序简单

0. 管道机制

作用:把不同的程序串联起来
例如:程序 aplusb 作用是读入两个整数a,b,返回 a+b 的值 程序 sqr 作用是读入一个整数 a,返回 a*a 的值
用管道机制表示为

  • echo 10 20 | ./aplusb | ./sqr
  • 格式 echo 传入参数 | ./接收函数 | ./接收函数 …

1. 精确数值

const double pi = acos(-1.0); //精确取 π 值 
//输出所有形如aabb的完全平方数。注意:a 的范围是1 ~ 9,但 b可以是 0 
//方法一: 
for(int a=0; a<=9; a++) 
{ 
  for(int b=0; b<=9; b++) 
  { 
    int n = a*1100+b*11; 
    int m = floor(sqrt(n)+0.5); 
    if(m*m == n) printf(“%d\n”, n); 
  } 
} 
//floor函数只取整数位,小数位舍弃 
//floor(x+0.5)为了四舍五入 不过这样小数部分0.5也会有误差 
//因此不能写 if( sqrt(n) == floor(sqrt(n)) ) printf(“%d\n”,n);

//方法二: 
for(int x=1; ;x++) 
{ 
  int n = x*x; 
  if (n < 1000) continue; 
  if (n > 9999) break; 
  int hi = n/100; 
  int lo = n%100; 
  if(hi/10 == hi%10 && lo/10 == lo%10) printf(“%d”,n); 
}

2. 输入输出框架

每次输入输出用标准输入「键盘输入」输出「显示器输出」太过于繁琐 采用输入输出数据存放在文件中来避免这种繁琐

//输入一些整数,求出它们的最小值、最大值和平均值(保留3位小数) 
//输入保证这些数都是不超过1000的整数 
//方法一:重定向 
#define LOCAL //注意:这里的宏定义即便没有赋值 也算定义了LOCAL 
#include
#define INF 1000000000 
int main() 
{ 
  #ifdefin LOCAL 
  freopen("data.in","r",stdin);//从这里开始所有键盘的输入改用文件 
  freopen("data.out","w",stdout);//从这里开始所有键盘的输出改用文件 
#endif 
  int x,n=0,min=INF,max=-INF,s=0; 
  while(scanf("%d",&x) == 1) 
  { 
    s += x; 
    if(xmax) max = x; 
    //printf("x=%d, min=%d, max=%d\n", x, min, max); 
    n++; 
  } 
  printf("%d %d %.3f\n", min, max, (double)s/n); 
  return 0; 
} 
//方法二:fopen 
#include 
#define INF 1000000000 
int main() 
{ 
  FILE fin, fout; 
  fin = fopen("data.in","rb");//fopen方法较灵活 
  fout = fopen("data.out","wb");//fin = stdin 便能切换到标准输入 
  int x, n=0, min = INF, max = -INF, s=0; 
  while(fscanf(fin, "%d", &x) == 1) 
  { 
    s += x; 
    if(x < min) min = x; 
    if(x > max) max = x; 
    n++; 
  } 
  fprintf(fout, "%d %d %.3f\n", min, max, (double)s/n); 
  fclose(fin); 
  fclose(fout); 
  return 0; 
}

3. 细节注意

C语言中 数据有不同的类型,因此 关系运算符 == 和 != 有严格的规定,必须同时考虑 数据类型数值大小

4. 关于 段

段:二进制文件内 的区域,所有特定类型信息被保存在里面

4.1 在可执行文件中

  • 正文段:存储指令
  • 数据段:存储全局变量「已初始化的」
  • BSS段:存储全局变量所需的空间「未初始化的」

4.2 在运行时

  • 堆栈段:程序动态创建,保存函数调用关系 和 局部变量
  • 因此栈溢出不一定是递归调用太多,也可能是局部变量太大

你可能感兴趣的:(「C 基础」编程习惯和窍门)