有时候,类比是非常有力的学习工具。
C#、Java和C++概要对比
对比点 |
C# |
Java |
C++ | |
特性 |
运行平台 |
虚拟机(.net framework CLR) |
虚拟机(jvm) |
操作系统 |
面向对象 |
天生支持 |
天生支持 |
通过扩展C支持 | |
继承父类数 |
单继承 |
单继承 |
多继承 | |
继承权限 |
只支持public继承 |
只支持public继承 |
可以指定继承权限(public,protect,private) | |
开源 |
开源资源相对较少 |
开源资源很多 |
开源资源相对少 | |
语言设计方向 |
对开发人员友好 |
对开发人员友好 |
对计算机友好 | |
使用思路 |
语言本身已集成很多设计模式,针对很多场景已提供现成解决方案,使用者可以把大部分精力专注在程序的架构设计方面。 |
使用者需要对设计模式等理论比较了解,需要消耗一定的精力解决一些详细设计问题,然后再考虑程序的架构设计。 |
使用者需要先消耗很多精力在语法、算法、操作系统等底层基础上,然后才能去考虑程序的详细设计和构架设计。 | |
学习曲线 |
易上手,不易学精。 |
不易上手,不易学精。 |
难上手,非常难精。 | |
适合领域 |
企业普适计算。 |
企业普适计算。 |
高性能计算、低层开发。 | |
编程效率 |
高 |
中 |
低 | |
运行效率 |
中 |
中 |
高 | |
主要资料来源 |
微软。 |
Oracle、IBM、BEA等许多厂商。 |
国际标准组织(ISO),及各路精英。 | |
垃圾回收 |
垃圾回收器(GC) |
垃圾回收器(gc) |
无。可使用智能指针。shared_ptr、unique_ptr | |
概念 |
中间语言 |
.net中间语言(IL) |
Java字节码(.class) |
无 |
标准组织 |
微软(提交国际标准组织认证) |
Java标准组织(Java Community Process) |
ISO的C++标准委员会 | |
运行时动态识别类型(RTTI)或动态创建新类型 |
使用“反射”实现动态查找使用现有类,使用“反射发出”实现动态创建新类型。 |
使用“反射”实现动态查找使用现有类。不直接支持运行时动态创建新类型,需借助javassist等库。 |
不支持动态查找,但MFC等库提供些类似功能。不支持运行时动态创建新类型。 | |
动态编译 |
编译器作为服务(Compiler as a Service) |
动态编译工具包(javax.tools complier) |
不支持。 | |
事件 |
多播委托,event关键字 |
没有直接支持。可用接口和匿名类实现。 |
没有直接支持,可用函数指针或MFC的CEvent等开发库。 | |
泛型 |
支持。在平台级别支持泛型编程,编译的中间语言IL中存在泛型类型。 |
支持。在语法级别支持泛型编程。编译的字节码不再区分具体泛型。 |
支持。在编译级别支持泛型编程。不同类型参数的模板会被编译成不同的实例 。 | |
闭包 |
lambda表达式,.NET 3.0开始支持 |
lambda表达式,Java 8开始支持 |
lambda表达式,C++ 11开始支持 | |
动态类型 |
dynamic关键字。DLR |
不支持。 |
不支持。 | |
类型 |
简单类型、引用类型 |
简单类型、引用类型 |
简单类型、指针类型、引用类型 | |
资源的集合 |
程序集。托管dll |
包。jar |
库。动态链接库(dll)、静态链接库(lib) | |
设计 |
文件夹与文件中类计数 |
文件夹只用来方便组织文件,不限制文件与类的对应关系。 |
文件夹与包对应,一个文件与一个public类对应。 |
文件夹只用来方便组织文件,不限制文件与类的对应关系。 |
类文件组织 |
以业务划分的观点组织类,把完成相同业务逻辑的类文件聚集在一起,不倾向使用嵌套类。 |
以类功能划分的观点组织类文件,把实现同一个类功能的类文件放在一起,较多的使用嵌套类以体现类与类的组合关系。 |
以模块划分的观点组织类,把完成相同程序功能的类文件聚集在一起,几乎不使用嵌套类。 | |
源文件扩展名 |
.cs |
.java |
.cpp,.h | |
桌面程序开发 |
WinForm、WPF… |
SWing、AWT、SWT… |
MFC… | |
网页程序开发 |
ASP.NET、ASP.NET MVC |
JSP |
CGI | |
浏览器插件 |
Silverlight |
Applet、JavaFX |
ActiveX | |
块开始标志 |
推荐大括号另起新行 |
推荐大括号不另起行 |
推荐大括号另起新行 | |
强制异常处理 |
不支持 |
checked exception |
不支持 | |
推荐方法命名 |
帕斯卡命名法 |
骆驼命名法 |
帕斯卡命名法 | |
推荐变量命名 |
骆驼命名法 |
骆驼命名法 |
匈牙利命名法 | |
语法 |
声明封闭类或封闭方法 |
sealed关键字 |
final关键字 |
final指示字,C++ 11开始支持。 |
声明常量/不变量 |
const,readonly关键字 |
final关键字 |
const关键字 | |
声明变量 |
具体类型声明具体类型对象,小写声明是大写声明类型的关键字。(Int32是实际类型,int是编译关键字) |
具体类型声明具体类型对象,小写声明是声明简单基础类型。(Interger是声明整形对象,int是声明简单整数类型) |
具体类型声明具体类型对象,全大写声明是宏,小写声明是声明类型。(INT是使用宏声明整形,int是使用关键字声明整形) | |
类型检查 |
.GetType() |
.class、.getClass() |
typeid() | |
类型识别 |
is |
instanceOf |
dynamic_cast | |
类型转换 |
使用()强制转换、 as关键字 |
使用()强制转换 |
使用()强制转换、 static_cast运算符、dynamic_cast运算符、reinterpret_cast运算符、const_cast运算符 | |
调用本类成员 |
this关键字 |
this关键字 |
this指针 | |
当前对象的父类引用 |
base关键字 |
super关键字 |
调用方法时显式指定父类名 | |
传参方式 |
简单类型传值的副本,复杂类型传引用的副本。可以使用ref、out进行更多控制。 |
简单类型传值的副本,引用类型传引用的副本。 |
显式指定传参方式。(传值、传指针、传引用、传右值) | |
文档注释 |
/// |
/** */ |
没有直接支持 | |
接口 |
interface |
interface |
使用纯虚类或宏 | |
switch表达式 |
byte、short、char、int、long、string或enum封装 |
byte、short、char、int或enum封装 |
int、char或enum封装 | |
goto |
允许但不推荐使用 |
不允许使用 |
允许但不推荐使用 | |
特性声明 |
attribute,使用[]符号 |
标注,使用@符号 |
attribute,使用[]符号 | |
访问权限修饰符 |
public、private、internel、protected |
public、private、protected |
public、private、protected、friend | |
操作符重载 |
支持 |
不支持 |
支持 | |
构造方法调用另外构造方法 |
在方法名后使用冒号操作符 |
在构造方法的第一句 |
在方法名后使用冒号操作符 | |
继承父类或接口 |
冒号操作符 |
extends关键字 |
冒号操作符 | |
重写父类方法 |
使用virtual、override关键字覆盖,使用new关键字隐藏。 |
只有override,默认全virtual。静态方法隐藏,实例方法覆盖。 |
virtual函数被覆盖,非virtual函数被隐藏。 | |
抽象 |
abstract关键字 |
abstract关键字 |
virtual 方法后加 = 0 标记 | |
同步锁 |
lock关键字 |
synchronized关键字 |
没有关键字直接支持 | |
索引 |
索引器 |
无 |
索引属性 | |
内部类 |
嵌套类 |
嵌套类、局部类 |
嵌套类、局部类 | |
静态类 |
支持,静态的是类本身。静态类用来封装静态方法,不可生成实例。 |
内部类才能静态,静态的是类标识。静态类用来在没有外部类实例的情况下生成内部类实例。 |
不支持 | |
部分类 |
使用partial关键字 |
不支持 |
天生支持 | |
字段get set操作 |
天生支持 |
不支持 |
不支持 | |
方法代理 |
委托(delegate) |
不直接支持,使用接口和包装类变通实现 |
函数指针 | |
断言 |
Trace.Assert方法 |
assert关键字 |
Assert宏 |
个人能力有限,如有疏漏之处,敬请指教。
谢谢。