反射机制

反射机制是在运行状态中,对于任意一个类,都能知道这个类(class文件)的所有属性和方法。
对于任意一个对象,都能调用它的任意一个方法和属性。
这种动态获取信息以及动态调用对象的方法的功能称为Java语言的反射机制。

简单来说,动态获取类中的信息,就是Java的反射机制。
可以理解为对类的解剖。

Tomcat
提供了处理请求和应答的方式。
因为具体的处理动作不同,所以对外提供了接口,由开发者来实现具体的请求和应答处理。

Class类可以获取字节码文件中的所有内容,反射就是依靠该类来完成的。
想要对一个类文件进行解剖,只要获取到该类的字节码文件即可。

获取类的字节码文件:

package cn.itcast.reflect.demo;import cn.itcast.bean.Person;/** 要想对字节码文件进行解剖,必须要有字节码文件对象*/
public class ReflectDemo {/*** @param args* @throws ClassNotFoundException */public static void main(String[] args) throws ClassNotFoundException {//        getClassObject_1();
//        getClassObject_2();getClassObject_3();}/** 方式三:(重点)* 只要通过给定的类的字符串名称,就可以获取该类,更为扩展。* 可以用Class类中的方法完成。* 该方法就是forName。* 各种方式只要有名称即可,更为方便,扩展性更强。*/public static void getClassObject_3() throws ClassNotFoundException {String className="cn.itcast.bean.Person";Class clazz=Class.forName(className);System.out.println(clazz);}/** 方式二:* 任何数据类型都具有一个静态的属性.class来获取其对应的Class对象。* 不需要构造函数。* 相对简单,但是还是需要明确用到类中的静态成员。* 不够扩展*/public static void getClassObject_2() {Class clazz=Person.class;Class clazz1=Person.class;System.out.println(clazz==clazz1);}/** 获取字节码对象的方式:* 方式一:* Object类中的getClass方法* 想要用这种方式,必须要明确具体的类,并创建对象。*/public static void getClassObject_1(){Person p=new Person();Class clazz=p.getClass();Person p1=new Person();Class clazz1=p1.getClass();System.out.println(clazz==clazz1);}}

获取Class中的构造函数:

package cn.itcast.reflect.demo;import java.lang.reflect.Constructor;public class ReflectDemo2 {/*** @param args* @throws Exception */public static void main(String[] args) throws Exception {// createNewObject();createNewObject_2();}public static void createNewObject_2() throws Exception {// cn.itcast.bean.Person p = new cn.itcast.bean.Person("小强",39);/** 当要获取指定名称对应类中的所体现的对象时,* 而该对象初始化不使用空参数构造函数* 既然是通过指定的构造函数进行兑现的初始化,* 应先获取到该构造函数。* 通过字节码文件即可完成* 该方法是:getConstructor(parameterTypes)*/String name = "cn.itcast.bean.Person";Class clazz = Class.forName(name);//获取到了指定的构造函数对象Constructor constructor=clazz.getConstructor(String.class,int.class);//通过该构造器对象的newInstance方法进行对象的初始化Object obj=constructor.newInstance("小明",38);}public static void createNewObject() throws ClassNotFoundException,InstantiationException, IllegalAccessException {// 早期:new的时候,先根据被new的类的名称查询该类的字节码文件,并加载进内存,并创建该字节码文件对象,然后创建该字节码文件对应的Person对象cn.itcast.bean.Person p = new cn.itcast.bean.Person();// 现在:String name = "cn.itcast.bean.Person";// 找寻该名称的类文件,并加载进内存,并产生Class对象Class clazz = Class.forName(name);// 如何产生该类的对象Object obj = clazz.newInstance();// 创建新实例}}

获取Class中的字段示例:
public class AccessibleObjectextends Object implements AnnotatedElement
AccessibleObject 类是 Field、Method 和 Constructor 对象的基类。它提供了将反射的对象标记为在使用时取消默认 Java 语言访问控制检查的能力。

package cn.itcast.reflect.demo;import java.lang.reflect.Field;public class ReflectDemo3 {/*** @param args* @throws Exception*/public static void main(String[] args) throws Exception {getFieldDemo();}/** 获取字节码文件中的字段*/public static void getFieldDemo() throws Exception {Class clazz = Class.forName("cn.itcast.bean.Person");// Field field=clazz.getField("age");//该方法只能获取到public的字段Field field=clazz.getDeclaredField("age");//只能获取本类中的所有字段(包含私有)//取消字段的访问权限检查,暴力访问field.setAccessible(true);Object obj=clazz.newInstance();field.set(obj, 90);Object o=field.get(obj);System.out.println(o);}}

获取Class中的方法:

package cn.itcast.reflect.demo;import java.lang.reflect.Constructor;
import java.lang.reflect.Method;import cn.itcast.bean.Person;public class ReflectDemo4 {/*** @param args* @throws Exception*/public static void main(String[] args) throws Exception {// getMethodDemo();// getMethodDemo_2();getMethodDemo_3();}public static void getMethodDemo_3() throws Exception {Class clazz = Class.forName("cn.itcast.bean.Person");Method method = clazz.getMethod("paramMethod", String.class, int.class);Object obj = clazz.newInstance();method.invoke(obj, "小强", 39);}public static void getMethodDemo_2() throws Exception {Class clazz = Class.forName("cn.itcast.bean.Person");Method method = clazz.getMethod("show", null);// 获取空参数一般方法// Person p=new Person();// p.show();// Object obj=clazz.newInstance();Constructor constructor = clazz.getConstructor(String.class, int.class);Object obj = constructor.newInstance("小明", 37);method.invoke(obj, null);}/** 获取指定Class中的公共函数*/public static void getMethodDemo() throws Exception {Class clazz = Class.forName("cn.itcast.bean.Person");Method[] methods = clazz.getMethods();// 获取的都是公有的方法methods = clazz.getDeclaredMethods();// 只获取本类中所有方法(包括私有)for (Method method : methods) {System.out.println(method);}}}

package cn.itcast.bean;public class Person {private int age;private String name;public Person(String name, int age ) {super();this.age = age;this.name = name;System.out.println("person param run..."+this.name+":"+this.age);}public Person() {super();System.out.println("person run");}public void show(){System.out.println(name+"...show run..."+age);}private void privateMethod(){System.out.println("private method run");}public void paramMethod(String str,int num){System.out.println("paramMethod run......"+str+":"+num);}public static void staticMethod(){System.out.println("staticMethod run");}
}

反射练习:

package cn.itcast.reflect.test;import java.io.File;
import java.io.FileInputStream;
import java.util.Properties;/** 电脑运行*/
public class ReflectTest {/*** @param args* @throws Exception */public static void main(String[] args) throws Exception {MainBoard mb=new MainBoard();mb.run();//每次添加设备都需要修改代码,传递新创建的对象
//        mb.usePCI(new SoundCard());//新增SoundCard,需要修改程序//不修改代码,就能够完成以上动作//不使用new,而是直接获取class文件,在内部实现创建对象的动作File configFile=new File("pci.properties");Properties prop=new Properties();FileInputStream fis=new FileInputStream(configFile);prop.load(fis);for(int x=0;x<prop.size();x++){String pciName=prop.getProperty("pci"+(x+1));Class clazz=Class.forName(pciName);//用Class去加载这个pci子类PCI p=(PCI) clazz.newInstance();//创建的对象肯定是PCI的子类,可以直接将创建的对象类型强转为PCImb.usePCI(p);}fis.close();}
}

package cn.itcast.reflect.test;public class MainBoard {public void run() {System.out.println("main board run");}public void usePCI(PCI p) {//多态,提高扩展性if (p != null) {p.open();p.close();}}
}package cn.itcast.reflect.test;public interface PCI {public void open();public void close();
}
package cn.itcast.reflect.test;public class SoundCard implements PCI{public void open(){System.out.println("sound open");}public void close(){System.out.println("sound close");}}
package cn.itcast.reflect.test;public class NetCard implements PCI{@Overridepublic void open() {System.out.println("net open");}@Overridepublic void close() {System.out.println("net close");}
}

pci.properties
pci1=cn.itcast.reflect.test.SoundCard
pci2=cn.itcast.reflect.test.NetCard

正则表达式
正则表达式用于操作字符串数据;
通过特定的符号来体现;
正则表达式虽然简化了书写,但是阅读性变差了。

package cn.itcast.regex.demo;public class RegexDemo {/*** @param args*/public static void main(String[] args) {String qq = "123456789";// checkQQ(qq);String regex = "[1-9][0-9]{4,14}";// 正则表达式// String regex="[1-9]\\d{4,14}";//正则表达式// boolean b=qq.matches(regex);// System.out.println(qq+":"+b);String str = "aoob";String reg = "ao+b";// o有一次或多次boolean b = str.matches(reg);System.out.println(b);}/** 需求:定义一个功能对QQ号进行校验* 要求:长度5-15位;只能是数字;0不能开头*/public static void checkQQ(String qq) {int len = qq.length();if (len >= 5 && len <= 15) {if (!qq.startsWith("0")) {try {long l = Long.parseLong(qq);System.out.println(qq + "正确");} catch (NumberFormatException e) {System.out.println(qq + "含有非法字符");}} else {System.out.println(qq + "不能0开头");}} else {System.out.println("长度错误");}}}

正则表达式对字符串的常见操作
组和捕获
捕获组可以通过从左到右计算其开括号来编号。例如,在表达式 ((A)(B(C))) 中,存在四个这样的组:

1     ((A)(B(C)))
2     \A
3     (B(C))
4     (C)

组零始终代表整个表达式。

之所以这样命名捕获组是因为在匹配中,保存了与这些组匹配的输入序列的每个子序列。捕获的子序列稍后可以通过 Back 引用在表达式中使用,也可以在匹配操作完成后从匹配器获取。

与组关联的捕获输入始终是与组最近匹配的子序列。如果由于量化的缘故再次计算了组,则在第二次计算失败时将保留其以前捕获的值(如果有的话)例如,将字符串 "aba" 与表达式 (a(b)?)+ 相匹配,会将第二组设置为 "b"。在每个匹配的开头,所有捕获的输入都会被丢弃。

以 (?) 开头的组是纯的非捕获 组,它不捕获文本,也不针对组合计进行计数。

public final class Patternextends Object implements Serializable
正则表达式的编译表示形式。
指定为字符串的正则表达式必须首先被编译为此类的实例(将正则表达式封装为对象)。然后,可将得到的模式用于创建 Matcher (匹配)对象,依照正则表达式,该对象可以与任意字符序列匹配。执行匹配所涉及的所有状态都驻留在匹配器中,所以多个匹配器可以共享同一模式。
因此,典型的调用顺序是
Pattern p = Pattern.compile("a*b");
Matcher m = p.matcher("aaaaab");
boolean b = m.matches();

package cn.itcast.regex.demo;import java.util.regex.Matcher;
import java.util.regex.Pattern;public class RegexDemo2 {/*** @param args*/public static void main(String[] args) {/** 正则表达式对字符串的常见操作* 1.匹配* 使用的是String类中matchs方法;* * 2.切割* 使用的是String类中的split方法;* * 3.替换* 使用的是String类中的replaceAll方法;* * 4.获取* 将正则规则进行对象的封装;* Pattern p = Pattern.compile("a*b");* 通过正则对象的matcher方法字符串相关联,获取要对字符串操作的匹配器对象Matcher* Matcher m = p.matcher("aaaaab");* 通过Matcher匹配器对象的方法对字符串进行操作* boolean b = m.matches();*/// functionDemo1();// functionDemo2();// functionDemo3();functionDemo4();}/** 获取示例*/public static void functionDemo4() {String str = "da jia hao,ming tian bu fang jia!";String regex = "\\b[a-z]{3}\\b";// \\b-单词边界,否则会出现jia hao    min的情况// 1.将正则封装成对象Pattern p = Pattern.compile(regex);// 2.通过正则对象获取匹配器对象Matcher m = p.matcher(str);// 使用Matcher对象的方法对字符串进行操作// 既然要获取三个字母组成的单词// 进行查找 find()方法System.out.println(str);while (m.find()) {System.out.println(m.group());// 获取匹配器的子序列System.out.println(m.start()+":"+m.end());//输出开始和结束的位置}}/** 替换示例*/public static void functionDemo3() {String str = "zhangsantttxiaoqiangmmmmmzhaoliu";// str=str.replaceAll("(.)\\1+", "#");//将叠词替换为#str = str.replaceAll("(.)\\1+", "$1");// 将叠词替换为一个字母;$1,获取第一个参数中的第一组System.out.println(str);String tel = "15812345678";// 158****5678tel = tel.replaceAll("(\\d{3})\\d{4}(\\d{4})", "$1****$2");System.out.println(tel);}/** 切割示例*/public static void functionDemo2() {// String str="zhangsan        xiaoqiang    zhaoliu";// String[] names=str.split(" +");//空格出现一次或多次// String str="zhangsan.xiaoqiang.zhaoliu";// String[] names=str.split("\\.");String str = "zhangsantttxiaoqiangmmmmmzhaoliu";// 按ttt,mmmmm切割// (X) X,作为捕获组 ;\n 任何匹配的 nth 捕获组// 组((A) (B(C)) 最外层括号为第一组,次外层为第二组,以此类推;无括号,则为第0组String[] names = str.split("(.)\\1+");// 第一位是任意字符,对任意字符进行复用for (String name : names) {System.out.println(name);}}/** 匹配示例*/public static void functionDemo1() {// 匹配手机号码是否正确String tel = "15800001111";// String regex="1[358][0-9]{9}";String regex = "1[358]\\d{9}";boolean b = tel.matches(regex);System.out.println(tel + ":" + b);}}

正则表达式-练习:

package cn.itcast.regex.test;import java.util.TreeSet;public class RegexTest {/*** @param args*/public static void main(String[] args) {/** 1.治疗口吃:我...我我要要...要要..要学...学...编编编程...程程...程程* 2.对ip地址排序* 3.对邮件地址校验*/
//        test_1();
//        test_2();test_3();}/** 邮箱地址校验*/public static void test_3() {String mail="abc1@sian.com.cn";String regex="[a-zA-Z0-9_]+@[a-zA-Z0-9]+(\\.[a-zA-Z]{2,3})+";//(\\.[a-zA-Z]{2,3})+,类似于.com,.cn的组,存在一次或者多次regex="\\w+@a\\w+(\\.\\w+)+";//笼统式匹配boolean b=mail.matches(regex);System.out.println(mail+":"+b);}/** ip地址排序* 192.168.10.34    127.0.0.1    3.3.3.3    105.70.11.55*/public static void test_2() {String ip_str="192.168.10.34  127.0.0.1 3.3.3.3    105.70.11.55";//1.为了让ip可以按字符串顺序比较,只要让ip的每一段位数相同,补零//按照每一位所需最多的0的个数进行补充;每一段都加2个0;ip_str=ip_str.replaceAll("(\\d+)", "00$1");
//        System.out.println(ip_str);//00192.00168.0010.0034  00127.000.000.001 003.003.003.003    00105.0070.0011.0055//2.每一段保留三位数字ip_str=ip_str.replaceAll("0*(\\d{3})", "$1");
//        System.out.println(ip_str);//192.168.010.034  127.000.000.001 003.003.003.003    105.070.011.055//切割ip地址String[] ips=ip_str.split(" +");TreeSet<String> ts=new TreeSet<String>();for(String ip:ips){ts.add(ip);}for(String ip:ts){System.out.println(ip.replaceAll("0*(\\d+)", "$1"));}}/** 治口吃*/public static void test_1(){String str="我...我我要要...要要..要学...学...编编编程...程程...程程";//1.将字符串中的 “.” 去掉,使用替换str=str.replaceAll("\\.+", "");//2.替换叠词str=str.replaceAll("(.)\\1+", "$1");System.out.println(str);}}

正则表达式-练习-爬虫

package cn.itcast.regex.test;import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;/** 网页爬虫:其实是一个用于在互联网中获取符合指定规则数据的程序* * 爬取邮箱地址*/
public class RegexTest2 {/*** @param args* @throws IOException*/public static void main(String[] args) throws IOException {// List<String> list=getMail();List<String> list = getMailByWeb();for (String mail : list) {System.out.println(mail);}}public static List<String> getMailByWeb() throws IOException {// 1.读取源文件URL url=new URL("http://iask.sina.com.cn/b/1005465.html");BufferedReader bufIn=new BufferedReader(new InputStreamReader(url.openStream()));// 2.对读取的数据进行规则的匹配,从中获取符合规则的数据String mail_regex = "\\w+@\\w+(\\.\\w+)+";List<String> list = new ArrayList<String>();Pattern p = Pattern.compile(mail_regex);String line = null;while ((line = bufIn.readLine()) != null) {Matcher m = p.matcher(line);while (m.find()) {// 3.将符合规则的数据存储到集合中list.add(m.group());}}bufIn.close();return list;}public static List<String> getMail() throws IOException {// 1.读取源文件BufferedReader bufr = new BufferedReader(new FileReader("c:\\mail.html"));// 2.对读取的数据进行规则的匹配,从中获取符合规则的数据String mail_regex = "\\w+@\\w+(\\.\\w+)+";List<String> list = new ArrayList<String>();Pattern p = Pattern.compile(mail_regex);String line = null;while ((line = bufr.readLine()) != null) {Matcher m = p.matcher(line);while (m.find()) {// 3.将符合规则的数据存储到集合中list.add(m.group());}}bufr.close();return list;}}

转载于:https://www.cnblogs.com/chenchong/archive/2012/08/18/2645964.html

Java语言基础-反射机制、正则表达式相关推荐

  1. [Java基础] 反射机制汇总

    引言 初学Java反射机制的时候,只是感觉很神奇,但是不知道学了该怎么用,所以过了一段时间就忘得差不多了:最近接触到了框架,在学习中遇到了反射,深深体会到了反射机制的神奇,回来复习了一下反射机制,写一 ...

  2. JAVA基础--JAVA中的反射机制详解

    JAVA反射机制     JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意一个方法:这种动态获取的信息以及动态调用对象的方法的功能 ...

  3. 根据实例详解Java中的反射机制

    概念: JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法:对于任意一个对象,都能够调用它的任意一个方法和属性:这种动态获取的信息以及动态调用对象的方法的功能称为java ...

  4. java 有哪些反射机制_Java 的反射机制你了解多少?

    不知道多少次听说过了Java反射机制的使用,比如:Spring 框架如何实例化IoC容器中的Bean,编码过程中如何动态的清理对象中的字段信息等等.工作中只是听说.看同事们编码实践,但是自己却只是概念 ...

  5. java代码安全检测机制_全面解析:java中的反射机制,内含代码验证解析

    什么是反射? 在运行状态中,对于任意一个类,都能够获取到这个类的所有属性和方法,对于任意一个对象,都能够调用它的任意一个方法和属性(包括私有的方法和属性),这种动态获取的信息以及动态调用对象的方法的功 ...

  6. JAVA Reflection(反射机制)

    Java 反射机制 反射机制简介 反射机制应用示例 简单的Ioc实现 代理模式 Java动态代理 简单的Aop实现 "程序运行时,允许改变程序结构或变量类型,这种语言称为动态语言" ...

  7. formdata 接受参数中带有class 对象_浅析JAVA中的反射机制及对Servlet的优化

    今天来聊聊java中的反射机制,工作以后发现很多东西动不动就要使用反射或者动态代理,如果不能很好的理解反射,那么对于动态代理等一些重要的设计模式就会有种不够通透的感觉. 所谓的反射,就是在运行状态中, ...

  8. Java反序列化之反射机制

    目录 前言 Java反射机制 反射机制方法 指定构造方法生成实例 执行私有方法 总结 前言 每次听到大佬在讲或者看论坛等一些方式学java反序列化漏洞时,都会有一个词叫做反射机制,大佬顺势借着这个词, ...

  9. Java动态性之反射机制(reflection)

    说到反射机制,第一次接触的人可能会比较懵,反射?什么反射?怎么反射?反射是干嘛的?下面我将在这篇文章中讲讲Java的反射机制 不过在这之前,还有一个问题需要解决,标题名中的动态性,说起动态性,我先介绍 ...

最新文章

  1. win10系统 计算机配置要求高吗,win10配置要求_win10配置要求高吗-太平洋电脑网
  2. module 'schedule' has no attribute 'every
  3. Redis学习之Docker环境搭建
  4. java的excel导出_java 实现excel 导出功能
  5. JavaScript学习之ES6学习之Promise
  6. 速达软件开发版使用技巧-每页固定行样式报表设计
  7. struts2+spring+mybatis简单配置
  8. H3C V7版本的系统默认权限
  9. 设置Emeditor为Python的简易开发工具
  10. Android服务器django,从ANDROID-STUDIO客户端与DJANGO服务器交谈
  11. python语言程序设计实验教程答案实验三_20194220 实验三《Python程序设计》实验报告...
  12. cmd 复制文件命令copy 复制目录树命令xcopy
  13. C#选择文件的对话框和选择文件夹的对话框
  14. psv无线怎么连接电脑连接服务器,如何使用PSV远程操作电脑 PSVITA REMOTE DESKTOP详细教程...
  15. iOS 仿微信发送语音消息按钮 - 语音录音机(二)
  16. sql 根据出生日期计算年龄
  17. Excel操作:制作to do list
  18. Echarts之饼图
  19. 2020面试准备之Java集合
  20. 【GANs学习笔记】(二十四)StyleGAN

热门文章

  1. 把合数分解成若干个质因数相成
  2. bzoj 3391: [Usaco2004 Dec]Tree Cutting网络破坏
  3. 二分最大匹配(匈牙利算法+HK算法)
  4. 图像形态学运算之图像开闭运算 含python实现
  5. 字符串-创建//比较
  6. Digilent提供的Pmod AD5驱动程序
  7. Backend Qt5Agg is interactive backend. Turning interactive mode on.
  8. linux服务器查看系统装到哪个盘,查看linux安装了什么服务器地址
  9. 20172329 2017-2018-2 《程序设计与数据结构》第五周学习总结
  10. php访问方法外变量