注:博客中内容主要来自《狄泰软件学院》,博客仅当私人笔记使用。
测试环境:Ubuntu 10.10
GCC版本:4.4.5
一、C与C++的关系
1) C++继承了所有的C特性
2) C++在C的基础上提供了更多的语法和特性
3) C++的设计目标是运行效率与开发效率的统一
二、C到C++的升级
1) C++更强调语言的实用性
升级了什么?
1.类型检查加强、函数的加强等等
2.面向对象支持
2) 所有的变量都可以在需要使用时再定义
int c = 0;
for(int i=1; i<=3 ; i++) //这里定义了变量
{
for(int j=1; j<=3; j++)
{
c += i*j;
}
}
对比:C语言中的变量都必须在作用域开始的位置定义!!
代码块中也可以定义变量
3) register关键字请求编辑器将局部变量存储于寄存器中(只是为了兼容C语言)
- 在C++中依然支持register关键字
- C++编辑器有自己的优化方式
c语言中无法获取register变量的地址
c++中可以取得register变量的地址
4) C++中的register关键字
C++编辑器发现程序中需要register变量的地址时,register对变量的声明变得无效。
早期C语言编辑器不会对代码进行优化,因此register变量是一个很好的补充。
5) 在C语言中,重复定义多个同名的全局变量是合法的(C语言中多个同名的全局变量最终会被链接到全局数据区的同一个地址空间上空间上;不允许多个局部变量重名)
6) 在C++中,不允许定义多个同名的全局变量(局部变量也不可以)
实例分析
C到C++的升级一
2-1.cpp
#include <stdio.h>
int g_v;
//int g_v; //如果这里不注释,就会提示重复定义
int main(int argc, char *argv[])
{
printf("Begin...\n");
int c = 0; //这里和C不同,C必须在函数开始位置
for(int i=1; i<=3; i++) //i在for循环内可以使用
{
for(int j=1; j<=3; j++)//j在for循环内可以使用
{
c += i * j;
}
}
printf("c = %d\n", c);
register int a = 0;
printf("&a = %p\n", &a);
printf("End...\n");
return 0;
}
操作:
1) 测试:1.访问register修饰变量的地址 2. 变量定义
g++ 2-1.cpp -o 2-1.out编译正常,打印结果:
Begin...
c = 36
&a = 0xbfd63f00
End...
2)代码移植到C中,gcc - c 2-1.c -o c2-1.out编译报错:
error: 'for' loop initial declarations are only allowed in C99 mode
for(int i=1; i<=3; i++)
for循环中初始化只在C99模式下允许
node: use option -std=c99 or -std=gnu99 to compile your code
使用-std=c99或者-std=gnu99来编译你的代码
error:'for' loop initial declarations are only allowed in C99 mode
for(int j=1; j<=3; j++)
for循环中初始化只在C99模式下允许
error:address of register variable 'a' requested
请求register修饰的变量a地址
分析:
1. C++支持for()中定义变量,C不支持这种方式(C99标准支持这种方式)。
2. C++允许访问register修饰的变量的地址,C语言不允许register修饰的变量地址。
3)测试:1. 重复定义变量
C++文件:
#include <stdio.h>
int g_v;
int g_v; //重复定义全局变量
int main(int argc, char *argv[])
{
printf("Begin...\n");
int c = 0;
int c = 0; //重复定义局部变量
for(int i=1; i<=3; i++)
{
for(int j=1; j<=3; j++)
{
c += i * j;
}
}
printf("c = %d\n", c);
printf("End...\n");
return 0;
}
编译:g++ 2-1.cpp -o 2-1.out
error: redefinition of 'int g_v'
int g_v:
错误:重复定义int g_v
error: 'int g_v'previously declared here
int g_v
错误:int g_v在这之前已经声明
error: redefinition of 'int c'
int c = 0;
错误:重复定义'int c'
error: 'int c' previously declared here
int c = 0;
错误:int c在这之前已经声明
代码移植到C文件,编译gcc -c 2-1.c -o c2-1.out:
2-1.c:11:6: error: redefinition of 'c'
int c = 0;
错误:重复定义'c'
2-1.c:10:6: note: previous definition of 'c' was here
int c = 0;
注意:在这之前(10行6列)定义了'c'
分析:
1. 全局变量C++不允许重复定义;C允许重复定义。
2. 局部变量C/C++都不允许相同作用域下定义相同变量名。
7) struct关键字的加强(重点)
- C语言中的struct定义了一组变量的集合
- C语言中的struct定义的标识符并不是一种新的类型
- C++中的struct用于定义一个全新的类型
8) C++中所有的标识符都必须显示的声明类型(C++是强类型语言,对语法检查很严格)
9) C语言中的默认类型C++中是不合法的
f(i)
{
printf("i = %d\n",i);
}
g()
{
return 5;
}
问题:
1.函数f的返回值和参数分别是什么类型?
2.函数g可以接受多少个参数?
三、面试中的小问题(重点)
int f()与int f(void)有有区别吗?如果有区别是什么?
在C语言中
- int f()表示返回值为int,接受任意参数的函数
- f(void)表示返回值为int的无参函数
在C++中
- int f()和int f(void)具有相同的意义,表示返回值为int的无参函数
实例分析
C到C++的升级二
2-2.cpp
#include <stdio.h>
struct Student //定义一个新的类型为结构体
{
const char* name;
int age;
}; //C中这里有变量名
f(i) //C++中错误
{
printf("i = %d\n", i);
}
g()
{
return 5;
}
int main(int argc, char *argv[])
{
Student s1 = {"Delphi", 30}; //这里在C语言中报错,不是类型。书写方式也不一样
Student s2 = {"Tang", 30}; //这里在C语言中报错,不是类型
f(10);
printf("g() = %d\n", g(1,2,3,4,5));
return 0;
}
操作:
1) g++ 2-2.cpp -o 2-2.out编译报错:
2-2.cpp:9:2: error:expected constructor, destructor, or type conversion
before '(' to ken
f(i)
错误:预期的构造函数,析构函数,或者类型转换
2-2.cpp:14:3: error: ISO C++ forbids declaration of 'g' with no type
g()
错误:ISO C++标准禁止声明'g'没有类型
2-2.cpp:25:6: error: 'f' was not declared in this scope f(10);
错误:'f'在这个范围没有声明。
2-2.cpp:27:34: error: too many arguments to function 'int g()'
printf("g() = %d\n", g(1,2,3,4,5));
错误:函数int g()有太多参数
2-2.cpp:14:1: note: declared here g()
错误:g()在这声明
2)代码移植到C文件中进行编译:gcc 2-2.c -o c2-2.out
2-2.c:21:2: error: unknown type name 'Student'
Student s1 = {"Delphi", 20};
错误:不知道'Student'类型名称
2-2.c:23:2: error: unknown type name 'Student'
Student s2 = {"Tang", 30};
错误:不知道'Student'类型名称
分析:
1. 注意int f()和int f(void)是一个意思,如果定义函数没有类型会报错。C++认为结构体是一种新的类型。C语言允许函数没有类型,参数没有认为允许接收任意类型。C语言认为结构体是一个类型。
小结
1) C++更强调实用性,可以在任意的地方声明变量
2) C++中的register只是一个兼容的作用
3) C++编译器能够更好的进行优化
4) C++中的任意标识符都必须显示的指明类型