C语言

C语言
维基百科,自由的百科全书
C,是一种通用的程序设计语言,它主要用来进行系统程序设计。具有高效、灵活、功能
丰富、表达力强和移植性好等的特点,在程序员中备受青睐。

C语言是由UNIX的研制者丹尼斯·里奇(Dennis Ritchie)和肯·汤普逊(Ken Thompson
)于1970年研制出的B语言的基础上发展和完善起来的。C语言可以广泛应用于不同的操
作系统,例如UNIX、MS-DOS、Microsoft Windows及Linux等。C语言是一种面向过程的语
言,同时具有高级语言和汇编语言的优点。在C语言的基础上发展起来的有支持多种程序
设计风格的C++语言,网络上广泛使用的Java、JavaScript,微软的C#等。

1983年,美国国家标准委员会(ANSI)对C语言进行了标准化,于1983年颁布了第一个C
语言标准草案(83 ANSI C),后来于1987年又颁布了另一个C语言标准草案(87 ANSI C
)。最新的C语言标准是在1999年颁布并在2000年3月被ANSI采用的 C99 ,但由于未得到
主流编译器厂家的支持,直到2004年C99 并未被广泛使用,增加了若干新特性后 C99 已
经逐渐让C语言和C++分道扬镳。

目录 [显示隐藏] 
1 C语言的特色

2 C语言的主要特性

3 C语言的历史

4 C语言的版本

4.1 K&R C
4.2 ANSI C和ISO C
4.3 C99


5 C语言的Hello World程序

6 进一步了解C

6.1 复合语句
6.2 条件语句
6.3 循环语句
6.4 跳转语句
6.5 在C99中运算符号


7 数据类型

7.1 基础数据类型
7.2 数组
7.3 指针
7.4 字符串
7.5 文件输入/输出


7.5.1 标准输入/输出


7.6 传递命令行参数


8 C语言的标准库

9 C语言的保留关键字
 
[编辑]
C语言的特色
C语言是系统程序语言.
C语言保留了低级语言的特性,例如涉及内存的指针。
使用了预处理机制,使得程序里可以通过包含例如宏处理的方式来处理源程序。
C语言的不足可以由C语言发展而来的更新的编程语言改进。Cyclone语言的拥有提防对于
内存错误的特性。C++和Objective C提供了用于面向对象的编程结构。Java和C#增加了
面向对象的结构使得对内存的管理自动化。

[编辑]
C语言的主要特性
C语言保留了低阶语言的特性,例如涉及内存的指标。
C语言通过参数在函数里传递数值。
使用了预处理机制,使得程序里可以通过包含例如宏处理的方式来处理根源程序。
C语言提供了一套标准库,这些库里提供了十分有用的功能。
但是并不是所有的这些特性都是有效的。例如,预处理通常作为一个独立的程序被处理
,这使得与处理的程序并不一定被完全编译。

虽然C是高阶语言,但是它同时拥有一些组合语言的特性,对其他的语言来说这是接近低
阶语言的特点。例如,在C语言里,程序师可以对计算机内存进行管理。在默认的情况下
,C语言不会对阵列的范围进行检查,也就是说即使阵列越界,C语言也不会作出错误提
示。对计算机内存的管理使得程序师可以变出更快捷、更有效的程序,这对于设备驱动
程序来说尤为重要。但是这也使得程序容易产生令人讨厌的“臭虫”,例如缓冲器溢出
错误。然而,这些错误可以由一些工具来避免。

C语言的不足可以由由C语言发展而来的更新的编程语言改进。Cyclone语言的拥有提防对
于内存错误的特性。C++和Objective C提供了用于面向物件的编程结构。Java和C#增加
了面向物件的结构使得对内存的管理自动化。

[编辑]
C语言的历史
C语言的第一次发展在1969年到1973年之间。C之所以被称为C是因为C语言的很多特性是
由一种更早的被称为B语言的编程语言中发展而来的。

到了1973年,C语言已经可以用来编写Unix操作系统的内核。这是第一次用C语言来编写
操作系统的内核。丹尼斯·里奇和Brian Kernighan在1978年出版了《C程序设计语言》
(The C Programming Language,经常简称为“白皮书”或“K&R”)。

1980年以后,贝尔实验室使得C变得更为广泛的流行,使得C一度成为了操作系统和应用
程序编程的首选。甚至到今天,它仍被广泛用于编写操作系统以及作为最广泛的计算机
教育的首选语言。

1980年代晚期,布贾尼·斯特劳斯特卢普和贝尔实验室为C语言添加了面向对象的特性.
这种语言成为了C++。C++现在广泛应用的在Microsoft Windows下运行的商业应用程序的
编制,然而C仍然是UNIX世界的热门编程语言。

[编辑]
C语言的版本
[编辑]
K&R C
C不断的从它的第一版本进行改进。在1978年,Kernighan和里奇的《C程序设计语言》第
一版出版。它介绍了下面的有关C语言版本的特性:

struct数据类型
long int数据类型
unsigned int数据类型
把运算符=+改为+=,依次类推。因为=+使得编译器混淆。
在以后的几年里,《C程序设计语言》一直被广泛作为C语言事实上的规范。在这本书中
,C语言通常被表述成“K&R C”。(第二版的包括了ANSI C标准)

K&R C通常被作为C编译器所支持的最基本的C语言部分。虽然现在的编译器并不一定都完
全遵循ANSI标准,但K&R C作为C语言的最底要求仍然要编程人员掌握。但是无论怎样,
现在使用广泛的C语言版本都已经与K&R C相距甚远了,因为这些编译器都使用ANSI C标
准。 //....

[编辑]
ANSI C和ISO C
1989年,C语言被ANSI标准化。(ANSI X3.159-1989)。标准化的一个目的是扩展K&R C
。这个标准包括了一些新的特性。在K&R出版后,一些新的特征被“非官方”的加到C语
言中。

void函数
函数返回struct或union类型
void *数据类型
在ANSI标准化自己的过程中,一些新的特征被加了进去。ANSI也标准了函数库。ANSI C
标准被ISO(国际标准化组织)采纳成为ISO 9899。ISO的第一个版本文件在1990年出版

[编辑]
C99
在ANSI标准化后,C语言的标准在一段相当的时间内都保持不变,尽管C++继续在改进。
(实际上,Normative Amendment1在1995年已经开发了一个新的C语言版本。但是这个版
本很少为人所知。)标准在90年代才经历了改进,这就是ISO9899:1999(1999年出版)
。这个版本就是通常提及的C99。它被ANSI于2000年三月采用。

在C99中包括的特性有:

对编译器限制增加了,比如源程序每行要求至少支持到 4095 字节,变量名函数名的要
求支持到 63 字节 (extern 要求支持到 31)
预处理增强了。例如:
宏支持取参数 #define Macro(...) __VA_ARGS__
使用宏的时候,参数如果不写,宏里用 #,## 这样的东西会扩展成空串。(以前会出错的
)
支持 // 行注释(这个特性实际上在C89的很多编译器上已经被支持了)
增加了新关键字 restrict, inline, _Complex, _Imaginary, _Bool
支持 long long, long double _Complex, float _Complex 这样的类型
支持 <: :> <% %> %: %:%: ,等等奇怪的符号替代,D&E 里提过这个
支持了不定长的数组。数组的长度就可以用变量了。声明类型的时候呢,就用 int a[*]
这样的写法。不过考虑到效率和实现,这玩意并不是一个新类型。所以就不能用在全局
里,或者 struct union 里面,如果你用了这样的东西,goto 语句就受限制了。
变量声明不必放在语句块的开头,for 语句提倡这么写 for(int i=0;i<100;++i) 就是
说,int i 的声明放在里面,i 只在 for 里面有效。
当一个类似结构的东西需要临时构造的时候,可以用 (type_name){xx,xx,xx} 这有点像
 C++ 的构造函数
初始化结构的时候现在可以这样写:
      struct {int a[3], b;} hehe[] =  { [0].a = {1}, [1].a = 2 };
      struct {int a, b, c, d;} hehe =  { .a = 1, .c = 3, 4, .b = 5}  // 3,4
是对 .c,.d 赋值的
字符串里面,/u 支持 unicode 的字符
支持 16 进制的浮点数的描述
所以 printf scanf 的格式化串多支持了 ll / LL (VC6 里用的 I64) 对应新的 long
long 类型。
浮点数的内部数据描述支持了新标准,这个可以用 #pragma 编译器指定
除了已经有的 __line__ __file__ 以外,又支持了一个 __func__ 可以得到当前的函数

对于非常数的表达式,也允许编译器做化简
修改了对于 / % 处理负数上的定义,比如老的标准里 -22 / 7 = -3, -22 % 7 = -1 而
现在 -22 / 7 = -4, -22 % 7 = 6
取消了不写函数返回类型默认就是 int 的规定
允许 struct 定义的最后一个数组写做 [] 不指定其长度描述
const const int i; 将被当作 const int i; 处理
增加和修改了一些标准头文件, 比如定义 bool 的 <stdbool.h> 定义一些标准长度的
int 的 <inttypes.h> 定义复数的 <complex.h> 定义宽字符的 <wctype.h> 有点泛型味
道的数学函数 <tgmath.h> 跟浮点数有关的 <fenv.h>。<stdarg.h> 里多了一个
va_copy 可以复制 ... 的参数。<time.h> 里多了个 struct tmx 对 struct tm 做了扩

输入输出对宽字符还有长整数等做了相应的支持
但是各个公司对C99的支持所表现出来的兴趣不同。当GCC和其它一些商业编译器支持C99
的大部分特性的时候,微软和Borland却似乎对此不感兴趣。

[编辑]
C语言的Hello World程序
下面是一个在标准输出设备上输出Hello World的简单程序,这种程序通常作为开始学习
编程语言时的第一个程序:

#include <stdio.h>

int main(void)
{
  printf("Hello, world!/n");
  return 0;
}
[编辑]
进一步了解C
C语言由函数和变量组成。C的函数就像是Fortran中的子程序和函数。

在C语言中,程序从main开始执行。main函数通过调用和控制其他函数进行工作。例如上
面的printf。程序员可以自己写函数,或从库中调用函数。在上面的return 0;使得main
返回一个值给调用程序的外壳,表明程序已经成功运行。

一个C语言的函数由返回值、函数名、参数列表(或void表示没有返回值)和函数体组成
。函数体的语法和其它的复合的语句部分是一样的。

[编辑]
复合语句
C语言中的复合语句的格式为:

{语句;语句;……}
复合语句可以使得几个语句变成一个语句。

[编辑]
条件语句
C语言有三种条件语句形式。两种是if,另一种是switch。

两种if包括:

if (条件表达式)
    语句;
以及

if (条件表达式)
    语句;
else
    语句;
在条件表达式中,任何非零的值表示条件为真;如果条件不满足,程序将跳过if后面的
语句,直接执行if后面的语句。但是如果if后面有else,则当条件不成立时,程序跳到e
lse处执行。

switch通常用于对几种有明确值的条件进行控制。它要求的条件值通常是整数或字符。
与switch搭配的条件转移是case。使用case后面的标值,控制程序将跳到满足条件的cas
e处一直往下执行,直到语句结束或遇到 break。通常可以使用default把其它例外的情
况包含进去。如果switch语句中的条件不成立,控制程序将跳到default处执行。switch
是可以嵌套的。

switch (<表达式>) {
    case <值1> :
        <语句>
    case <值2> :
        <语句>
    default :
        <语句>
}
[编辑]
循环语句
C语言有三种形式的循环语句:

do
    <语句>
while (<表达式>);
while (<表达式>)
    <语句>;
for (<表达式1> ; <表达式2> ; <表达式3>)
    <语句>;
在while和do中,语句将执行到表达式的值为零时结束。在do...while语句中,循环体将
至少被执行一次。这三种循环结构可以互相转化:

for (e1; e2; e3)
     s;
相当于

e1;
while (e2) {
    s;
    e3;
}
当循环条件一直为真时,将产生死循环。

[编辑]
跳转语句
跳转语句包括四种:goto,continue,break和return。

goto语句是无条件转移语句:

goto 标记

标记必须在当前函数中定义,使用“标记:”的格式定义。程序将跳到标记处继续执行
。由于goto容易产生阅读上的困难,所以应该尽量少用。

continue语句用在循环语句中,作用是结束当前一轮的循环,马上开始下一轮循环。

break语句用在循环语句或switch中,作用是结束当前循环,跳到循环体外继续执行。但
是使用break只能跳出一层循环。在要跳出多重循环时,可以使用goto使得程序更为简洁

当一个函数执行结束后要返回一个值时,使用return。return可以跟一个表达式或变量
。如果return后面没有值,将执行不返回值。

[编辑]
在C99中运算符号
() [] -> . ! ++ -- (cast)  括号、成员、逻辑非、自加、自减、强制转换
++ -- * & ~ ! + - sizeof  单目运算符
* / % 算术运算符
+ -  算术运算符
<< >> 位运算符
< <= > >= 关系运算符
== != 关系运算符号
& 位与
^ 位异或
| 位或
&& 逻辑与
|| 逻辑或
?: 条件运算符
= += -= *= /= %= <<= >>= &= |= ^= 赋值运算符
, 顺序运算符
[编辑]
数据类型
[编辑]
基础数据类型
注意:以下是典型的数据位长和范围。但是编译器可能使用不同的数据位长和范围。这
取决于使用的编译器。请参考具体的参考手册。

在头文件<limits.h>和<float.h>中说明了基础数据的长度。float,double和long
double的范围就是在IEEE 754标准中提及的典型数据。

关键字 位长 范围
char 1 -128..127 or 0..255
unsigned char 1 0..255
signed char 1 -128..127
int 2 or 4 -32768..32767 or
-2147483648..2147483647
short int 2 -32768..32767
long int 4 -2147483648..2147483647
float 4 ???
double 8 ???
long double 8 ???
[编辑]
数组
如果一个变量名后面跟着一个有数字的中括号,这个声明就是数组声明。字符串也是一
种数组。它们以ASCII的NUL作为数组的结束。

例如:

int myvector [100];
char mystring [80];
float mymatrix [3] [2] = {2.0 , 10.0, 20.0, 123.0, 1.0, 1.0}
int notfull [3][3] = {{1},{1,2,3},{4,5}} (*)
char lexicon [10000] [300] ; /* 共一千个最大长度为300的字符数组。*/
int a[3][4];
上面最后一个例子创建了一个数组,但也可以把它看成是一个多维数组。注意数组的下
标从0开始。这个数组的结构如下:

a[0][0] a[0][1] a[0][2] a[0][3]
a[1][0] a[1][1] a[1][2] a[1][3]
a[2][0] a[2][1] a[2][2] a[2][3]


例子(*)创建了一个3*3的二维数组,初始化时有些元素并未赋值.如下:

1 0 0
1 2 3
4 5 0

为0的位置的数值是随机的.

[编辑]
指针
如果一个变量声明时在前面使用*号,表明这个变量是一个指针。

例如:

int *pi; /* 指向整型数据的指针 */
int *api[3]; /* 由指向整型数据的指针构成的数组,长度为3 */
char **argv; /* 指向一个字符指针的指针 */
储存在指针中的地址所指向的数值在程序中可以由*读取。例如,在第一个例子中,*pi
是一个整型数据。这叫做引用一个指针。

另一个运算符&,叫做取地址运算符,它将返回一个变量、数组或函数的存储地址。因此
,下面的例子:

int i, *pi; /* int and pointer to int */
pi = &i;
i和*pi在程序中可以相互交替使用,直到pi被改变成指向另一个变量的指针。

[编辑]
字符串
要使用字符串并不需要引用库,但是C标准库确实包含了一些用于对字符串进行操作的函
数,使得它们看起来就像字符串而不是数组。使用这些函数需要引用头文件<string.h>


strcat(dest, source) - 连接两个字符串,把source加到dest末尾。
strchr(s, c) -在字符串c中找出字符s第一次出现的位置。当没有找到时,返回Null。

strcmp(a, b) - 比较字符串a和b的大小。如果两个字符串相同,返回0;如果a>b,返回
正数;如果a<b,返回负数。
strcpy(dest, source) - 把字符串source拷贝到字符串dest中。
strlen(st) - 返回字符串st的长度。
strncat(dest, source, n) - 把source中的n个字符追加到dest后面。null后面的值将
不会被添加。
strncmp(a, b, n) - 比较字符串a和b中n个字符的大小。如果两个字符串相同,返回0;
如果a>b,返回正数;如果a<b,返回负数。
strncpy(dest, source, n) - 把字符串source拷贝到字符串dest中。(最多拷贝n个)

strrchr(s, c) - 在s中查找最后一次出现c的位置。返回这个位置。如果找不到,返回n
ull。
[编辑]
文件输入/输出
在C语言中,输入和输出是经由标准库中的一组函数来实现的。在ANSI/ISO C中,这些函
数被定义在头文件<stdio.h>中。

[编辑]
标准输入/输出
有三个标准输入/输出是预定义的:

stdin 标准输入
stdout 标准输出
stderr 输入输出错误
这些定义在运行过程中是自动的打开和关闭的,所以它们并不需要进行显式定义。

下面的这个例子显示了一个过滤程序(filter program)是怎样构成的。

#include <stdio.h>
int main()
{
        int c;
        while (( c = getchar()) != EOF ) {
        /* 对字符进行各种处理 */
                if (anErrorOccurs) {
                        fputs("an error eee occurred/n", stderr);
                        break;
                }
                putchar(c);
        }
}
[编辑]
传递命令行参数
在命令行赋予程序的参数将通过在main()函数中定义一个整型参数(int)和一个指向字
符指针的指针型参数(char **)来实现,前者传递命令行参数的个数,后者传递命令行
参数内容。习惯上将这两个参数分别命名为argc和argv。程序文件名被作为第一个命令
行参数。

对于下列程序:

#include <stdio.h>
int main(int argc, char **argv) {
  int i;
  for(i=0;i<argc;i++)
    printf("%d:%s/n",i,argv[i]);
  return 0;
}
输入命令(假设该程序生成C:/TC/a.exe): a one two three

则会得到下面的输出结果:

0:C:/TC/A.EXE
1:one
2:two
3:three
[编辑]
C语言的标准库
以下列出由C语言提供的标准函数库,函数库通过#include进行引用。

在C89标准中:

<assert.h>
<ctype.h>
<errno.h>
<float.h>
<limits.h>
<locale.h>
<math.h>
<setjmp.h>
<signal.h>
<stdarg.h>
<stddef.h>
<stdio.h>
<stdlib.h>
<string.h>
<time.h>
在95年的修正版中

<iso646.h>
<wchar.h>
<wctype.h>
在C99中增加了六个函数库

<complex.h>
<fenv.h>
<inttypes.h>
<stdbool.h>
<stdint.h>
<tgmath.h>
[编辑]
C语言的保留关键字
char short int unsigned
long float double struct
union void enum signed
const volatile typedef auto
register static extern break
case continue default do
else for goto if
return switch while sizeof
 

 
--
是故易有太極。是生兩儀。兩儀生四象。
四象生八卦。八卦定吉凶。吉凶生大業。
※ 来源:·我爱南开站 nkbbs.org·[FROM: 10.13.5.5]
 

 

freshrain(02CS~~祝NKBBS永远年轻) 2005年05月27日08:29:05 星期五
心随心动--GCC的发展之路(zzCSDN) 回复 寄信 转寄 转贴 同主题
 
http://www.csdn.net/subject/gcc/
 不经意间,GCC已发展到了4.0的版本,尽管在软件开发社区之外乏人闻问,但因为GCC在
几乎所有开源软件和自由软件中都会用到,因此它的编译性能的涨落会直接影响到
Linux 、Firefox 乃至于OpenOffice.org和Apache等几千个项目的开发。因此,把GCC摆
在开源软件的核心地位是一点也不为过。另一方面,GCC4.0的出现,正在牵引着广大程序
员们的心。如果我们非要用一个词来说明GCC与程序员之间的关系,那无疑是"心随心
动"。

历史篇 作为自由软件的旗舰项目,Richard Stallman 在十多年前刚开始写作 GCC 的时
候,还只是把它当作仅仅一个 C 程序语言的编译器;GCC 的意思也只是 GNU C
Compiler 而已。经过了这么多年的发展,GCC 已经不仅仅能支持 C 语言;它现在还支
持 Ada 语言、C++ 语言、Java 语言、Objective C 语言、Pascal 语言、COBOL语言,以
及支持函数式编程和逻辑编程的 Mercury 语言,等等。而 GCC 也不再单只是 GNU C 语
言编译器的意思了,而是变成了 GNU Compiler Collection 也即是 GNU 编译器家族的意
思了。另一方面,说到 GCC 对于各种硬件平台的支持,概括起来就是一句话:无所不
在。几乎所有有点实际用途的硬件平台,甚至包括有些不那么有实际用途的硬件平台。

Gcc 简介
Linux系统下的gcc(GNU C Compiler)是GNU推出的功能强大、性能优越的多平台编译
器,是GNU的代表作品之一。Gcc是可以在多种硬体平台上编译出可执行程序的超级编译
器,其执行效率与一般的编译器相比平均效率要高20%~30%。

GCC 3.0印象记
从1999年4月开始,GCC的含义从GNU C Compiler变成了GNU Compiler Collection,支持
C、C++、Objective C、Chill、Fortan和Java等语言。其中C++编译器G++当然是我们关注
的焦点。从GCC网站的介绍中可以看出,G++作了不少改进,更好地支持C++标准。我们将
选出相关的内容逐一评论。我们对GCC 3.0的总体印象是,有不少改进,但"革命尚未成
功",还得加把劲儿。
技术篇 GCC是整个协作软件开发理念的基础,时至今日,GCC的使用范围已不仅仅限于
Linux平台,而是扩展到了包括Windows在内的很多平台。这样,GCC性能的高低,还关系
到许多专有软件的核心竞争力。

Linux上安装GCC编译器过程

在cygwin下安装gcc4.0

GCC--一切从这里开始
要想读懂本文,你需要对C语言有基本的了解,本文将介绍如何使用gcc编译器。首先,我
们介绍如何在命令行方式下使用编译器编译简单的C源代码。然后,我们简要介绍一下编
译器究竟作了那些工作,以及如何控制编译过程。我们也简要介绍了调试器的使用方
法。

GCC 中文手册

GCC中SIMD指令的应用方法
X86架构上的多媒体应用开发,如果能够使用SIMD指令进行优化, 性能将大大提高。目
前,IA-32的SIMD指令包括MMX,SSE,SSE2等几级。 在GCC的开发环境中,有几种使用
SIMD指令的方式……

GCC常用命令描述

Gcc使用的内嵌汇编语法格式小教程
本文对内嵌汇编语法,从基本语法、内嵌汇编的格式介绍、和扩展的内嵌汇编格式进行了
详细说明,需要说明的是gcc采用的是at&t的汇编格式。
现状篇 GCC4.0的发展道路并不平坦。GCC 4.0发布不久就因为无法编译Linux图形界面
KDE,而遭到参与开发KDE的程序员们的放弃。但是,一方面,GCC4.0编译性能的提高,是
有目共睹的。另一方面,开源软件的一大优势,就在于它能在开发者的不断改进中变得完
善。

开源开发工具GCC将大翻修 性能有望全面提升
改良GCC 并非易事,从GCC 3.3 版升级到3.4 版,在性能上虽然有进步,但却造成回溯兼
容性的问题。GCC4.0在这方面又做得如何呢?

开源利器GCC 4.0性能改进工作火热进行
GCC 4.0发布不久就遇到问题,Linux图形界面KDE无法用GCC编译,参与开发KDE的程序员
们随即放弃了GCC 4.0。这些问题又如何解决呢?
调查篇

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值