Java 反射机制[Method反射]

接着上一篇Java 反射机制[Field反射],通过调用Person类的setName方法将obj的name字段的Value设置为"callPersonSetNameMethod"来了解什么是Method反射。演示样例代码非常简单,非常easy理解。

能够看到Method.invoke()实际上并非自己实现的反射调用逻辑,而是托付给sun.reflect.MethodAccessor来处理。 真正的反射是调用MethodAccessor.invoke()真正完毕反射调用。看源代码能够发现MethodAccessor.invoke() 方法中出现了非常多跟Cached有关的变量,说明method的反射十分消耗性能。

Java Code

/*

* System Abbrev :

* system Name  :

* Component No  :

* Component Name:

* File name     :ReflectTestMain.java

* Author        :Qiuzhenping

* Date          :2014-10-25

* Description   :  <description>

*/



/* Updation record 1:

 * Updation date        :  2014-10-25

 * Updator          :  Qiuzhenping

 * Trace No:  <Trace No>

 * Updation No:  <Updation No>

 * Updation Content:  <List all contents of updation and all methods updated.>

 */

package com.qiuzhping.reflect.main;



import java.lang.reflect.Constructor;

import java.lang.reflect.Field;

import java.lang.reflect.InvocationTargetException;

import java.lang.reflect.Method;

import java.lang.reflect.Modifier;





/**

 * <Description functions in a word>

 * 反射就是把Java类中的各种成分映射成对应的Java类。

 * <Detail description>

 *

 * @author  Qiuzhenping

 * @version  [Version NO, 2014-10-25]

 * @see  [Related classes/methods]

 * @since  [product/module version]

 */

public class ReflectTestMain {



    /** <default constructor>

     */

    public ReflectTestMain() {

        // TODO Auto-generated constructor stub

    }



    /** <Description functions in a word>

     * 2014-10-25

     * <Detail description>

     * @author  Qiuzhenping

     * @param args [Parameters description]

     * @return void [Return type description]

     * @exception throws [Exception] [Exception description]

     * @see [Related classes#Related methods#Related properties]

     */

    public static void main(String[] args) throws Exception{

        // TODO Auto-generated method stub

        //Constructor[] contructor = Person.class.getConstructors();

        //Method[] method = Person.class.getMethods();

        Person p = new Person(24, "Qiuzhping", "100001", "Qiuzhping");

//        Field [] field = p.getClass().getDeclaredFields();

//        for(Field f:field){

//            f.setAccessible(true);

//            System.out.println(f.getName());

//            Object obj = f.get(p);

//            System.out.println(obj);

//        }

        changeStringValue(p);

        System.out.println(p.toString());

        callPersonSetNameMethod(p);

        System.out.println(p.toString());

    }



    /** <Description functions in a word>

     *  通过调用Person类的setName方法将obj的name字段的Value设置为"callPersonSetNameMethod"来了解什么是Method反射<BR>

     *  2014-10-26

     * <Detail description>

     * @author  Qiuzhenping

     * @param obj

     * @throws Exception [Parameters description]

     * @return void [Return type description]

     * @exception throws [Exception] [Exception description]

     * @see [Related classes#Related methods#Related properties]

     */

    private static void callPersonSetNameMethod(Object obj) throws Exception {

        Method[] methods = Person.class.getMethods();//获取所有方法

        for(Method m : methods){

            m.setAccessible(true);//暴力反射

            if(m.getName().equals("setName")){

                m.invoke(obj, "callPersonSetNameMethod");//将obj的name字段的Value设置为"callPersonSetNameMethod"

                /**

                 * 下面是Java method关于invoke方法的源代码

                 * 能够看到Method.invoke()实际上并非自己实现的反射调用逻辑,而是托付给sun.reflect.MethodAccessor来处理。


                 * 真正的反射是调用MethodAccessor.invoke()真正完毕反射调用。

                 * 看源代码能够发现MethodAccessor.invoke() 方法中出现了非常多跟Cached有关的变量,

                 * 说明method的反射十分消耗性能

                 *  public Object invoke(Object obj, Object... args)

                throws IllegalAccessException, IllegalArgumentException,

                       InvocationTargetException

                {

                    if (!override) {

                        if (!Reflection.quickCheckMemberAccess(clazz, modifiers)) {

                            Class caller = Reflection.getCallerClass(1);

                            Class targetClass = ((obj == null || !Modifier.isProtected(modifiers))

                                                 ? clazz

                                                 : obj.getClass());

            

                    boolean cached;

                    synchronized (this) {

                        cached = (securityCheckCache == caller)

                            && (securityCheckTargetClassCache == targetClass);

                    }

                    if (!cached) {

                        Reflection.ensureMemberAccess(caller, clazz, obj, modifiers);

                        synchronized (this) {

                        securityCheckCache = caller;

                        securityCheckTargetClassCache = targetClass;

                        }

                    }

                        }

                    }

                    if (methodAccessor == null) acquireMethodAccessor();

                    return methodAccessor.invoke(obj, args);

                }

                 * */

            }

        }

    }



    /** <Description functions in a word>

     *  将obj对象中的String类型的字段相应的Value中含有i的字符替换为abc<BR>

     *  2014-10-26

     * <Detail description>

     * @author  Qiuzhenping

     * @param obj [Parameters description]

     * @return void [Return type description]

     * @exception throws [Exception] [Exception description]

     * @see [Related classes#Related methods#Related properties]

     */

    private static void changeStringValue(Object obj) throws Exception {

        Field[] fields = obj.getClass().getDeclaredFields();

        for(Field f : fields){

            f.setAccessible(true);//暴力反射

            if(f.getType() == String.class){//字节码比較是用 ==

                String oldValue = (String) f.get(obj);

                String newValue = oldValue.replaceAll("i", "abc");//将全部的i替换为abc

                f.set(obj, newValue);

            }

        }

        

    }

    

     static class Person {



        public Person(int age, String name, String id, String pwd) {

            super();

            this.age = age;

            this.name = name;

            this.id = id;

            this.pwd = pwd;

        }

        @Override

        public String toString() {

            return "age = "+age +"\tname = "+name+"\tid = "+id+"\tpwd = "+pwd;

        }

        private int age;

        private String name;

        private String id;

        private String pwd;

        public int getAge() {

            return age;

        }

        public void setAge(int age) {

            this.age = age;

        }

        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;

        }

        public String getPwd() {

            return pwd;

        }

        public void setPwd(String pwd) {

            this.pwd = pwd;

        }

        /** <default constructor>

         */

        public Person() {

            // TODO Auto-generated constructor stub

        }



    }



}

Java 反射机制[Method反射]的更多相关文章

  1. Java 反射机制[Field反射]

    Java 反射机制[Field反射] 1.  反射概念及功能 反射就是把Java类中的各种成分映射成对应的Java类.比如一个Java类中用一个Class类的对象来表示. 一个类中的组成部分分为成员变 ...

  2. java反射机制 + Method.invoke解释 getMethod + 反射理解

    功能: 通过读取另一个Dll去创建一个控件(Form,Button,TextBox,DataGridView),然后对当中一些属性进行检查. 创建控件的大致流程是,Assembly->Modul ...

  3. Java RTTI机制与反射机制

    1.1 什么是RTTI? 维基百科的定义:In computer programming, RTTI (Run-Time Type Information, or Run-Time Type Iden ...

  4. java 类加载机制和反射机制

    一.类的加载机制 jvm把class文件加载到内存,并对数据进行校验.解析和初始化,最终形成jvm可以直接使用的java类型的过程.(1)加载         将class文件字节码内容加载到内存中, ...

  5. 一篇文章看懂java反射机制(反射实例化对象-反射获得构造方法,获得普通方法,获得字段属性)

    Class<?> cls = Class.forName("cn.mldn.demo.Person"); // 取得Class对象传入一个包名+类名的字符串就可以得到C ...

  6. 回顾反射机制Method

    package com.demo.service; public interface SayHello { void sayHello(String name); } 接口实现类 package co ...

  7. [Java反射机制]用反射改进简单工厂模式设计

    如果做开发的工作,工厂设计模式大概都已经深入人心了,比较常见的例子就是在代码中实现数据库操作类,考虑到后期可能会有数据库类型变换或者迁移,一般都会对一个数据库的操作类抽象出来一个接口,然后用工厂去获取 ...

  8. Java高级特性——反射机制(完结)——反射与注解

    按照我们的学习进度,在前边我们讲过什么是注解以及注解如何定义,如果忘了,可以先回顾一下https://www.cnblogs.com/hgqin/p/13462051.html. 在学习反射和注解前, ...

  9. Java学习之反射机制及应用场景

    前言: 最近公司正在进行业务组件化进程,其中的路由实现用到了Java的反射机制,既然用到了就想着好好学习总结一下,其实无论是之前的EventBus 2.x版本还是Retrofit.早期的View注解框 ...

随机推荐

  1. 墙内安装nautilus-dropbox 1.6.0-2

    软件包:nautilus-dropbox 版本号:1.6.0-2 # aptitude install nautilus-dropbox # less `which dropbox` 查找到下载链接: ...

  2. 关于Linux系统清理/tmp/文件夹的原理

    转自:http://www.opsers.org/base/clean-up-on-the-linux-system-tmp-folder-you-may-want-to-know.html 我们知道 ...

  3. centos7安装codeblocks教程

    author:lidabo 装了好多次系统,每次装的时候都有要在网上各种查,太麻烦了.所以决定记录一下,以后用到的时候会方便一些.当然,本文来源于网络,取百家之长,最重要的是本人已验证过,说明对本系统 ...

  4. [Android系列—] 1. Android 开发环境搭建与Hello World

    前言 開始之前先熟悉几个名词: SDK -- Software Development Kit, 软件开发工具包.这个词并不陌生, JDK,就是Jave Development Kit,相同对于And ...

  5. delphi如何加上spliter分割条,任意调整大小

    如题1:如何把一个panel分割成四个小的panle 2:也就是如何加上spliter,分割条,任意调整大小 3.如何有独立的handle使用多个总共5个为什么呢,你放4个panel 然后放split ...

  6. android studio 怎么运行java

    方法/步骤 1.新建一个project,或者如果已经有project的话,那就直接新建一个module.注意选择Java library,然后下一步 2.输入module的一些信息.点击finish ...

  7. JS实现图片翻书效果

    picture.html <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http- ...

  8. JQuery - MD5加密

    效果: JS代码: 命名为任意名称,一般为:Jquery.md5.js /** * jQuery MD5 hash algorithm function * * <code> * Calc ...

  9. 14.19 InnoDB and MySQL Replication InnoDB 和MySQL 复制:

    14.19 InnoDB and MySQL Replication InnoDB 和MySQL 复制: MySQL 复制工作对于InnoDB 表和对于MyISAM表. 它是可能使用复制的方式 存储引 ...

  10. JavaScript 进阶(四)解密闭包closure

    闭包(closure)是什么东西 我面试前端基本都会问一个问题"请描述一下闭包".相当多的应聘者的反应都是断断续续的词,“子函数”“父函数”“变量”,支支吾吾的说不清楚.我提示说如 ...