Javaweb中提到的反射浅析(附源码)
反射:一个jdk5.0的新特性,高级运用。在后期的框架中,这个是一大重点,现在估计我们都不会太多的接触他的。但是为了后面的铺垫,我想还是先了解一下:
先构造一个类,然后我们用反射来获取,调用里面的方法,属性
package com.changeyd.test09;
public class Person {
// 属性
private String name;
private String id;
// 没有参数的构造方法
public Person() {
}
public Person(String name, String id) {
super();
this.name = name;
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
}
好了,创建好类了,就可以构造一个Test来获取它的内容了:
哦。。对对对,在运用前,先得了解一下反射的基本原理:
一:反射的原理
*应用在一些通用性比较高的代码中
*在后期中的框架中,大多数都是使用反射来实现的
*在框架开发中,都是基于配置文件开发
**在配置文件中配置了类,可以通过反射得到类中的所有内容,可以让类中的某个方法来执行
*类中的所有内容:属性、没有参数的构造方法,有参数的构造方法、普通方法
**反射的原理:
*首先需要把java文件保存到本地硬盘 .java
*编译java文件,成 .class文件
*使用jvm,把class文件通过类加载加载到内存中
*万事万物皆对象,class文件到内存中使用Class类表示
*当使用反射时候,首先需要获取到Class类,得到这个类之后,就可以得到clss文件里面的所有内容了
-包含属性 构造方法 普通方法
*属性通过一个类:Filed
*构造方法通过一个类:Constructor
*普通方法通过一个类:Method
二:现在就可以获取第一步,无参方法
使用反射操作类里面的无参数的构造方法
*首先获取到Class类
// 获取class类
Class class1 = Person.class;
Class class2 = new Person().getClass();
Class class3 = Class.forName("com.changeyd.test09.Person");
*比如:对一个类型进行实例化,可以new,如果不使用new,如何获取?
//得到class类
Class class1 = Class.forName("com.changeyd.test09.Person");
//得到Person类的实例
Person person = (Person) class1.newInstance();
-代码:
//操作无参数的构造方法
@Test
public void test1() throws ClassNotFoundException, InstantiationException, IllegalAccessException{
//得到class类
Class class1 = Class.forName("com.changeyd.test09.Person");
//得到Person类的实例
Person person = (Person) class1.newInstance();
//设置值
person.setName("Wangji");
System.out.println(person.getName());
}
三:使用反射操作有参数的构造方法
//操作有参数的构造方法
@Test
public void test2() throws NoSuchMethodException, SecurityException, ClassNotFoundException, InstantiationException,
IllegalAccessException, IllegalArgumentException, InvocationTargetException {
// 得到class类
Class class1 = Class.forName("com.changeyd.test09.Person");
// 使用有参数的构造方法
// class1.getConstructors();//获取所有的构造方法
Constructor cs = class1.getConstructor(String.class, String.class);
// 通过有参数的构造方法设置值
// 通过有参数的构造方法来创建Person实例
Person person = (Person) cs.newInstance("lisi", "100");
System.out.println(person.getId() + " " + person.getName());
}
四:使用反射来操作属性
* @Test
public void test3() throws IllegalArgumentException, IllegalAccessException, NoSuchFieldException,
SecurityException, InstantiationException {
try {
// 得到class类
Class class1 = Class.forName("com.changeyd.test09.Person");
// 得到name属性
// class1.getDeclaredFields();//表示得到所有的属性
// 得到Person类的实例
Person person = (Person) class1.newInstance();
//通过这个方法得到属性,参数是属性的名称
Field field = class1.getDeclaredField("name");
//操作的是私有的属性,不让操作,需要设置可以操作私有属性setAccessible(true),可以操作私有属性
field.setAccessible(true);
// 设置name值 set方法,两个参数:第一个参数类的实例,第二个参数是设置的值
field.set(person, "wangwu");// 相当于在p.name = "wangwu";
System.out.println(field.get(person)); // 相当于p.name;
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
五:使用泛型来操作普通方法
*使用Method来表示普通方法
*代码
// 普通方法,比如操作 setName
@Test
public void test4() throws IllegalAccessException, IllegalArgumentException, InvocationTargetException,
NoSuchMethodException, SecurityException, InstantiationException, ClassNotFoundException {
// 得到Class类
Class class1 = Class.forName("com.changeyd.test09.Person");
// 得到Person的实例
Person person = (Person) class1.newInstance();
// 得到普通方法
// class1.getDeclaredFields();//得到所有的普通方法
//传递两个参数:第一个参数,方法名称;第二个参数,通过方法设置的值
Method method = class1.getDeclaredMethod("setName", String.class);
// 让setName方法执行,执行设置值
//使用invoke(person, "niuqi");传递两个参数;第一个参数,person实例;第二个参数,设置的值
//执行了invoke方法之后,相当于,执行了setName方法,同事通过这个方法设置了一个值是niuqi。
method.invoke(person, "niuqi");
System.out.println(person.getName());
}
在里面还需要一些注意的地方:
//如果操作的是私有的方法,需要设置值为true
method.setAccessible(true);
*当操作的方法是静态的方法时候,因为静态方法调用的方式是 类名.方法名,不需要类的实例
*使用反射操作静态方法的时候,也是不需要实例
*在invoke方法的第一个参数里面,写一个null
-method.invoke(null, "wangji");
对于反射中,原理很重要,先了解,但是对于反射,这些只是皮毛,在进入框架,才有具体的认识
Javaweb中提到的反射浅析(附源码)的更多相关文章
- V8中的快慢数组(附源码、图文更易理解😃)
接上一篇掘金 V8 中的快慢属性,本篇分析V8 中的快慢数组,了解数组全填充还是带孔.快慢数组.快慢转化.动态扩缩容等等.其实很多语言底层都采用类似的处理方式,比如:Golang中切片的append操 ...
- Lazy<T>在Entity Framework中的性能优化实践(附源码)
在使用EF的过程中,导航属性的lazy load机制,能够减少对数据库的不必要的访问.只有当你使用到导航属性的时候,才会访问数据库.但是这个只是对于单个实体而言,而不适用于显示列表数据的情况. 这篇文 ...
- Android中Canvas绘图基础详解(附源码下载) (转)
Android中Canvas绘图基础详解(附源码下载) 原文链接 http://blog.csdn.net/iispring/article/details/49770651 AndroidCa ...
- Vue路由实现之通过URL中的hash(#号)来实现不同页面之间的切换(图表展示、案例分析、附源码详解)
前言 本篇随笔主要写了Vue框架中路由的基本概念.路由对象属性.vue-router插件的基本使用效果展示.案例分析.原理图解.附源码地址获取. 作为自己对Vue路由进行页面跳转效果知识的总结与笔记. ...
- 在网站开发中很有用的8个 jQuery 效果【附源码】
jQuery 作为最优秀 JavaScript 库之一,改变了很多人编写 JavaScript 的方式.它简化了 HTML 文档遍历,事件处理,动画和 Ajax 交互,而且有成千上万的成熟 jQuer ...
- Web 开发中很实用的10个效果【附源码下载】
在工作中,我们可能会用到各种交互效果.而这些效果在平常翻看文章的时候碰到很多,但是一时半会又想不起来在哪,所以养成知识整理的习惯是很有必要的.这篇文章给大家推荐10个在 Web 开发中很有用的效果,记 ...
- Entity Framework在Asp.net MVC中的实现One Context Per Request(附源码)
上篇中"Entity Framework中的Identity map和Unit of Work模式", 由于EF中的Identity map和Unit of Work模式,EF体现 ...
- javaweb异常提示信息统一处理(使用springmvc,附源码)
一.前言 后台出现异常如何友好而又高效地回显到前端呢?直接将一堆的错误信息抛给用户界面,显然不合适. 先不考虑代码实现,我们希望是这样的: (1)如果是页面跳转的请求,出现异常了,我们希望跳转到一个异 ...
- 在Winform窗体中使用WPF控件(附源码)
原文:在Winform窗体中使用WPF控件(附源码) 今天是礼拜6,下雨,没有外出,闲暇就写一篇博文讲下如何在Winform中使用WPF控件.原有是我在百度上搜索相关信息无果,遂干脆动手自己实现. W ...
随机推荐
- Smarty 变量修饰器
为了更方便的实现 功能与显示分离,通常会用 smarty 将功能代码中的数据 assign 到页面中,在页面中合理使用 smarty 的修饰方法,会使页面显示更美观! 一个数据可同时使用多个修饰函数, ...
- linux学习之centos(三):mysql数据库的安装和配置
前言:mysql简介 说到数据库,我们大多想到的是关系型数据库,比如mysql.oracle.sqlserver等等,这些数据库软件在windows上安装都非常的方便,在Linux上如果要安装数据库, ...
- python主成分分析
#-*- coding: utf-8 -*- #主成分分析 降维 import pandas as pd #参数初始化 inputfile = '../data/principal_component ...
- mysql的主主复制详解
Mysql双主部署 解释: 所谓双主备份,其实也就是互做主从复制,每台master既是master,又是另一台服务器的slave.这样,任何一方所做的变更,都会通过复制应用到另外一方的数据库中. 要求 ...
- js history
後退:退到歷史列表的前一個url,和瀏覽器點擊後退按鈕功能相同 history.back() 前進:進入歷史列表的後面一個url,和瀏覽器的前進按鈕功能相同 history.forward()
- Guava的RateLimiter在单机限流中的正确用法
错误使用 在实现限流时,网上的各种文章基本都会提到Guava的RateLimiter,用于实现单机的限流,并给出类似的代码: public void method() { RateLimiter ra ...
- Bootstrap手风琴效果
前面的话 Bootstrap 框架中 Collapse插件(折叠)其实就是我们常见的手风琴效果.当单击一个触发元素时,在另外一个可折叠区域进行显示或隐藏,再次单击时可以反转显示状态.经典的场景是多个折 ...
- Nginx referer防盗链模块
L75 referer模块 ngx_http_referer_module 默认编译进nginx valid_referers 指令 Syntax: valid_referers none | blo ...
- [USACO 2010 Open Silver 3.Time Travel]——链表
Description 约翰得到了一台时光机,他可以用这台机器回到过去(但不能到未来),改变他家的牛群.约翰 打算依次进行 N 步操作,每步操作分为三种: • 买入操作以 a 表示,后接一个参数 i, ...
- BZOJ2004 HNOI2010公交线路(状压dp+矩阵快速幂)
由数据范围容易想到矩阵快速幂和状压. 显然若要满足一辆公交车的相邻站台差不超过p,则每相邻p个站台中每辆车至少经过一个站台.可以发现这既是必要的,也是充分的. 开始的时候所有车是相邻的.考虑每次把一辆 ...