什么是反射?
以下是摘自百度百科的关于java的反射的定义:
Java的反射(reflection)机制是指在程序的运行状态中,可以构造任意一个类的对象,可以了解任意一个对象所属的类,可以了解任意一个类的成员变量和方法,可以调用任意一个对象的属性和方法。这种动态获取程序信息以及动态调用对象的功能称为Java语言的反射机制
简言之,在运行时可以获取对象的状态,以及改变状态等。
c++为什么需要反射
C++目前是不支持反射特性的,C++20目前来看也是没有的。那么反射特性到底能做什么,举个例子,设计模式中经常讲IoC,将对象的初始化放在同一的容器之中,减少业务代码之间的依赖,降低耦合度,其中以工厂方法为例:
class
上面factory根据传入的type的值,初始化person对象并返回,但是当新增person,需要再次修改factory函数。但是如果支持反射,则有更好一点的解决方案,java语言具有反射特性,接下来看一下java怎样处理上面的工厂函数:
public class Person {
public String attr = "Person";
public static Object factory(String type) {
try {
Class<?> classz = Class.forName(type);
return classz.getDeclaredConstructor().newInstance();
} catch (Exception ex) {
ex.printStackTrace();
}
return null;
}
public static void main(String[] args) {
//System.out.println(args.toString());
Person person = (Person)factory(args[0]);
System.out.println("***********");
System.out.println(person.attr);
System.out.println("***********");
}
}
class Teacher extends Person {
Teacher() {
attr = "Teacher";
}
}
class Student extends Person {
Student() {
attr = "Student";
}
}
javac Person.java
$ java Person "Student"
***********
Student
***********
$ java Person "Teacher"
***********
Teacher
***********
$ java Person "Person"
***********
Person
***********
可以看到java根据传入的参数,利用反射特性,自动生成对象。
java利用反射,除了上面的例子之外,能做更多的事,比如,解析mySql数据库配置文件自动初始化sqlSession对象。尤其是spring框架的出现,将java的生态进一步的扩大,而spring正是建立在反射的基础之上的,可以看到现在java的服务端编程,基本上都离不开spring了,spring的家族正在不断地壮大,springMVC,springBoot……
总结
个人在使用C++和java的过程中,感觉java对C++很大的一个优势就在于java支持反射和注解,有了反射和注解java衍生出了很多很多的框架,生态非常地繁荣,而这正是C++所欠缺的。大家也都经常说C++很难,其实语法就那么些东西,把C++primer和effective C++看一遍,基本上不会有什么大的问题,涉及到比较麻烦的比如内存管理,一般在项目中基本不会让直接new内存的,要么是内存池,要么是智能指针了,或者容器。
当然,一些开源的C++库是支持反射的,比如protobuf。期待反射出现在下一次的c++标准中。