黑马程序员——java高新技术--反射
来源:互联网 发布:淘宝7.1.0版本官方网 编辑:程序博客网 时间:2024/04/28 02:04
------Java培训、Android培训、iOS培训、.Net培训、期待与您交流! -------
反射
1、Class2、反射 3、Constructor 4、Filed 5、Method
6、调用主函数7、数组 8、文件加载 9、集合 11、内省
反射
1、Class
Java中的所有类属于同一事物,描述该事物的类就是Class。Class反射的基石.
Class创建的实例是内存中字节码。字节码就是我们平常所说的类。
获得字节码有三种方式:
Person.class
new Person().getClass()
Class.forName("")
String s="abc";//获得字节码有三种方式Class s1=s.getClass();//从内存中获得Class s2=String.class;//知道类名去加载class文件,然后从内存中获得Class s3=Class.forName("java.lang.String");//不知道类名,传一个类名,然后去加载class文件,然后从内存中获得System.out.println(s1==s2);System.out.println(s2==s3);//三种方式获得为同一字节码System.out.println(String.class.isPrimitive());System.out.println(int.class.isPrimitive());System.out.println(int[].class.isArray());System.out.println(Integer.TYPE);//基本类型的TYPE字段2、反射
反射就是把java类中的各种成分映射成java类。
java类中的成分,对应的类有:Field,Method,Contructor,Package...
3、Constructor
类代表某个类中的一个构造方法。获得的方式,一个类中很多个构造方法,怎么获得自己想要的那一个呢?
用参数类型来区分。
构造方法的获得比较耗性能,反射会引起性能下降。
//用反射实现new String(new StringBuffer("abc"));Constructor constructor1=String.class.getConstructor(StringBuffer.class);//得到String的一个构造函数,有一个参数,类型为StringBufferString ss=(String)constructor1.newInstance(new StringBuffer("abc"));System.out.println(ss.charAt(1));
4、Filed
表示类中字段这类事物。通过getField方法获得类中的成员,然后获得具体对象中的值。权限不同,获取成员及成员在对象上的值的操作不同。举例如下:
public class ReflectPoint {public int x;private int y;public ReflectPoint(int x, int y) {this.x = x;this.y = y;}}
非私有成员:
//获得rp对象上的x值ReflectPoint rp=new ReflectPoint(3,5);Field fx=ReflectPoint.class.getField("x");//返回的是成员System.out.println(fx.get(rp));私有成员:
//获得rp对象上的y值Field fy=ReflectPoint.class.getDeclaredField("y");//只要你声明了 ,我就能拿到fy.setAccessible(true);//暴力反射,强制访问System.out.println(fy.get(rp));练习:
<span style="white-space:pre"></span>// 一个修改字符串的小程序// 将字符值中得b修改为apublic static void changeStrigValue(Object object) throws Exception {Field[] fields = object.getClass().getFields();for (Field field : fields) {if (field.getType() == String.class) {String oldValue = (String) field.get(object);String newValue = oldValue.replace('b', 'a');field.set(object, newValue);// System.out.println(newValue);}}System.out.println(object);}
5、Method
//s.charAt(0);Method methodcharAt=String.class.getMethod("charAt", int.class);System.out.println(methodcharAt.invoke(s, 0));
System.out.println(methodcharAt.invoke(s, new Object[]{0}));
6、调用主函数
//TestArgs.main(new String[]{"111","222","333"});String startClassName=args[0];Method mainMethod=Class.forName(startClassName).getMethod("main", String[].class);mainMethod.invoke(null, (Object)new String[]{"111","222","333"});mainMethod.invoke(null, new Object[]{new String[]{"111","222","333"}});
class TestArgs{<span style="white-space:pre"></span>public static void main(String[] args){<span style="white-space:pre"></span>for(String s:args)<span style="white-space:pre"></span>System.out.println(s);<span style="white-space:pre"></span>}}7、数组
//数组的反射public static void arrayReflet(Object obj){Class clazz=obj.getClass();//反射的前提是得到字节码,根据字节码进行相关的操作if(clazz.isArray()){int length=Array.getLength(obj);for(int i=0;i<length;i++){System.out.println(Array.get(obj, i));}}else{System.out.println("obj");}}
8、文件加载
A.从PC加载不是用硬编码,而是生成的目录(用户配置的选择)+在项目中得位置:FileInputStream("相对 :因为无法得知用户的选择,故只是相对用户选择的一个路径")
B.从classPath加载
(1):用类加载器:*.class.getLoader().getResourcesAs("classPath下的绝对路径");
(2):用类直接加载:*.class.getLoader().getResourcesAs("classPath下的绝对路径");
(3):用类直接加载:*.class.getLoader().getResourcesAs("classPath下的绝对路径");
public class ReflectTest {/** * @param args */public static void main(String[] args) throws Exception{// TODO Auto-generated method stub/*getRealPath();//金山词霸/内部一定要记住用完整的路径,但完整的路径不是硬编码,而是运算出来的。*///InputStream ips = new FileInputStream("config.properties");//InputStream ips = ReflectTest2.class.getClassLoader().getResourceAsStream("cn/itcast/day1/config.properties");//InputStream ips = ReflectTest2.class.getResourceAsStream("resources/config.properties");InputStream ips = ReflectTest2.class.getResourceAsStream("/cn/itcast/day1/resources/config.properties");Properties props = new Properties();props.load(ips);ips.close();String className = props.getProperty("className");Collection collections = (Collection)Class.forName(className).newInstance();//Collection collections = new HashSet();ReflectPoint pt1 = new ReflectPoint(3,3);ReflectPoint pt2 = new ReflectPoint(5,5);ReflectPoint pt3 = new ReflectPoint(3,3);collections.add(pt1);collections.add(pt2);collections.add(pt3);collections.add(pt1);//pt1.y = 7;//collections.remove(pt1);System.out.println(collections.size());}}
9、集合
Hashcode()的作用:
修改Hash值
对象默认的Hash值,与对象在内存中的地址有关,Hash值是为了Hash集合检索方便,使用Hash算法,把Hash集合内部分成若干区域,每个区域的给一个Hash值与对象的Hash值对应;
所以,只有使用Hash集合它才有价值;
所以,要使两个对象在Hash集合中的引用是同一个,就的用Hashcode()方法修改Hash值;
注意:已存入Hash集合的对象,不能再修改Hash值有关的字段值,会引起内存泄露。
String className = (String) props.getProperty("className");Collection collection = (Collection) Class.forName(className).newInstance();// Collection collection=new HashSet();collection.add(pt1);collection.add(pt2);collection.add(pt3);collection.add(pt4);// pt1.x=6;// collection.remove(pt1);System.out.println(collection.size());
10、内省
intorspection内省,用来操作javaBean。
编写Person的javaBean:
public class Person(){public int age;public int getAge(){return age;}public void setAge(int age){this.age=age;}获取javaBean属性的方法:如果第二个字母是小写,则把set&get后第一个字母变成小写;如果第二个字母是大写,则把保持大写;eg: settime-->time(??)setTime-->timesetTIME-->TIME}//主要用到PropertyDescriptor,来操作javaBean的set&get方法private static void setObject(Object rp, String propertyName, Object object)throws Exception {PropertyDescriptor pd2= new PropertyDescriptor(propertyName, rp.getClass());Method methodSetX=pd2.getWriteMethod();methodSetX.invoke(rp,object);}private static Object getObject(Object rp, String propertyName)throws IntrospectionException, IllegalAccessException,InvocationTargetException {PropertyDescriptor pd= new PropertyDescriptor(propertyName, rp.getClass());Method methodGetX=pd.getReadMethod();Object retValue=methodGetX.invoke(rp);return retValue;}// 复杂的内省public static Object getObject2(Object rp,String propertyName) throws Exception{Object retValue = null;PropertyDescriptor[] pds = Introspector.getBeanInfo(rp.getClass()).getPropertyDescriptors();for (PropertyDescriptor pd : pds) {if (pd.getName().equals(propertyName)) {Method methodGet = pd.getReadMethod();retValue = methodGet.invoke(rp);break;}}return retValue;}
- 黑马程序员——【Java】【高新技术】反射
- 黑马程序员java高新技术——反射
- 黑马程序员——java高新技术:反射
- 黑马程序员——Java高新技术---反射
- 黑马程序员——java高新技术--反射
- 黑马程序员——Java高新技术---反射
- 黑马程序员——Java高新技术---反射
- 黑马程序员—JAVA高新技术之反射
- 黑马程序员—JAVA高新技术_反射
- 黑马程序员—【Java高新技术】之反射
- 黑马程序员——java高新技术——反射
- 黑马程序员——java高新技术——反射
- 黑马程序员——Java高新技术——反射机制
- 黑马程序员——JAVA高新技术——反射
- 黑马程序员——Java高新技术视频笔记:反射
- 黑马程序员——Java高新技术_反射
- 黑马程序员——高新技术---Java基础-反射
- 黑马程序员——java高新技术之反射
- 三国群英传——哪些官职可以不封?
- C#中隐式接口与显示接口
- 在iOS7以后的状态栏设置样式
- HTML颜色代码表
- (1185)POJ-状态压缩
- 黑马程序员——java高新技术--反射
- Swift 复数变量定义
- 改变自己,带动激情,让人生更有意义
- iOS app在启动过程的设置图片的规格
- 英语语法 可作主语的词类 1.1.2代词作主语
- 初学Android, spinner
- HTML中一些漂亮的特殊字符
- 插入排序、归并排序、快速排序的比较和分析
- NYOJ 698 A Coin Problem (斐波那契)