码迷,mamicode.com
首页 > 其他好文 > 详细

反射,工厂模式

时间:2015-03-16 19:17:04      阅读:193      评论:0      收藏:0      [点我收藏+]

标签:

该类不能运行,执行Test方法,需要空构造函数
demo3: 调用指定构造方法
demo2: 调用默认构造方法
demo1: 获得.class 字节码对象,对应Class对象. 3种方法
工厂模式: 使用接口, 接收通过工厂类返回来的实例对象. 工厂类通过读取配置文件,来决定实例化哪个类
package com.xiaofan.test;

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;

import org.junit.Test;

public class ClassTest {
    public ClassTest(int a) {
    }
// 类构造实例,调用指定构造方法 @Test public void demo3() throws ClassNotFoundException, SecurityException, NoSuchMethodException, IllegalArgumentException, InstantiationException, IllegalAccessException, InvocationTargetException { // 已知类情况下,通过new 创建实例 ClassTest classTest = new ClassTest(10); // 1. 获得字节码对象 Class c = Class.forName("com.xiaofan.test.ClassTest"); // 2. 获得指定构造方法 Constructor constructor = c.getConstructor(int.class); // 3、调用构造方法 获得对象 Object o = constructor.newInstance(10); }
// 类构造实例,默认构造方法 @Test public void demo2() throws ClassNotFoundException, InstantiationException, IllegalAccessException { // 已知类情况下,通过new 创建实例 ClassTest classTest = new ClassTest(10); // 未知类和对象情况下 String classDescription = "com.xiaofan.test.ClassTest"; Class c3 = Class.forName(classDescription); Object classTest2 = c3.newInstance(); // 执行默认构造方法 } // 获得一个.class 字节码文件 对应Class类对象 @Test public void demo1() throws ClassNotFoundException { // 已知类情况下 获得字节码对象 Class c1 = ClassTest.class; // 已知一个对象,但是不知道这个对象属于哪个类,获得字节码对象 Object o = new ArrayList(); Class c2 = o.getClass(); // 等价于 ArrayList.class // 未知类和对象情况下 String classDescription = "com.xiaofan.test.ClassTest"; Class c3 = Class.forName(classDescription); } }

-----------------------------------------------------------------------------------------------

 

通过反射获取成员变量,执行类中方法

package com.xiaofan.test;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

import org.junit.Test;

public class FieldMethodTest {
    private int num;

    public void m(String s) {
        System.out.println("反射测试的方法!" + s);
    }
    /**
     * 通过反射的方式执行类中的方法
     */
    @Test
    public void demo2() throws ClassNotFoundException, InstantiationException,
            IllegalAccessException, SecurityException, NoSuchMethodException,
            IllegalArgumentException, InvocationTargetException {
        // 以前方式
        FieldMethodTest fieldMethodTest = new FieldMethodTest();
        fieldMethodTest.m("001");
        // 1. 获得Class对象
        Class c = Class.forName("com.xiaofan.test.FieldMethodTest");
        // 2、获得对象
        Object o = c.newInstance();
        // 3. 获得m对象反射中Method对象
        Method m = c.getMethod("m", String.class);
        // 4. 调用o对象m方法
        m.invoke(o, "008");
    }

    /**
     * 通过反射获取成员变量,修改私有变量是可见的
     */
    @Test
    public void demo1() throws ClassNotFoundException, SecurityException,
            NoSuchFieldException, InstantiationException,
            IllegalAccessException {
        // 以前方法操作变量
        FieldMethodTest fieldMethodTest = new FieldMethodTest();
        fieldMethodTest.num = 10;
        // 1、获得字节码文件
        Class c = Class.forName("com.xiaofan.test.FieldMethodTest");
        // 2、获得num成员变量 对应反射对象 Field
        Field[] fields = c.getFields(); // 获得所有public属性
        System.out.println(fields.length);
        Field[] fields2 = c.getDeclaredFields(); //获得所有成员变量
        System.out.println(fields2.length);
        Field field = c.getDeclaredField("num");
        // 3. 为num 赋值
        Object o = c.newInstance(); // 调用默认构造方法
        // 修改私有变量是 可见的
        field.setAccessible(true);
        field.set(o, 20);
        System.out.println(field.get(o));
    }
}

-------------------------------------------------------------------------------------------------------

 

自动装配

package com.xiaofan.test;

import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;

import org.junit.Test;

public class AutowireTest {
    @Test
    public void demo1() throws Exception {
        Map<String, String> map = new HashMap<String, String>();
        map.put("name", "小丽");
        map.put("hobby", "音乐");
        map.put("age", "20");
        Person person = new Person();
        autowire(person, map);
        System.out.println(person.getName());
        System.out.println(person.getHobby());
        User user = new User();
        autowire(user, map);
        System.out.println(user.getName());
        System.out.println(user.getAge());

    }

    public void autowire(Object o, Map<String, String> map) throws Exception {
        // 获得map 所有key
        Set<String> keys = map.keySet();
        // 获得Object中所有属性
        // 获得Class对象
        Class c = o.getClass();
        // 获得所有属性
        Field[] fields = c.getDeclaredFields();
        for (Field field : fields) {
            // 获得属性名称
            String fieldName = field.getName();
            // 判断属性名称是否存在于map的key
            if (map.containsKey(fieldName)) {
                // 完成属性封装
                String value = map.get(fieldName);
                // 修改私有属性可见性
                field.setAccessible(true);
                field.set(o, value);
            }
        }
    }
}

class User {
    private String name;
    private String age;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getAge() {
        return age;
    }

    public void setAge(String age) {
        this.age = age;
    }

}

class Person {
    private String name;
    private String hobby;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getHobby() {
        return hobby;
    }

    public void setHobby(String hobby) {
        this.hobby = hobby;
    }

}

------------------------------------------------------------------------------------------------

 工厂模式,测试类:

 

package com.xiaofan.demo;

import org.junit.Test;

import com.xiaofan.demo.impl.Fenggong;
import com.xiaofan.demo.impl.Liuqian;
import com.xiaofan.demo.impl.Wangfei;
import com.xiaofan.demo.impl.Yangliping;

public class EveningParty {

    /**
     * 使用工厂模式,从配置文件中实例化所需要的对象
     * @throws Exception
     */
    @Test
    public void demo2() throws Exception {
        // 对于估计要做事情,定义接口 ---- 不变的
        // 变化的是 实现类

        // 1. 歌曲类
        Singer singer = Factory.findSinger(); // 工厂
        singer.sing();
        // 2. 舞蹈类
        Dancer dancer = Factory.findDancer();
        dancer.dance();
        // 3、语言类
        Speaker speaker = Factory.findSpeaker();
        speaker.speak();
        // 4、动作类
        Actor actor = Factory.findActor();
        actor.action();
    }

    /**
     * 传统方式,紧密耦合
     */
    @Test
    public void demo1() {
        // 对于估计要做事情,定义接口 ---- 不变的
        // 变化的是 实现类
        
        // 1. 歌曲类
        Singer singer = new Wangfei(); // 紧密耦合
        singer.sing();
        // 2. 舞蹈类
        Dancer dancer = new Yangliping();
        dancer.dance();
        // 3、语言类
        Speaker speaker = new Fenggong();
        speaker.speak();
        // 4、动作类
        Actor actor = new Liuqian();
        actor.action();
    }
}

工厂类:

package com.xiaofan.demo;

import java.util.ResourceBundle;

import com.xiaofan.demo.impl.Liuqian;
import com.xiaofan.demo.impl.Yangliping;
import com.xiaofan.demo.impl.Zhaobenshan;

public class Factory {
    public static Singer findSinger() throws Exception {
        // return new Wangfei(); 
        // 上面是传统模式,下面使用工厂模式返回实例对象
        // className = com.xiaofan.demo.impl.Zhangxueyou
        // ResourceBundle: 资源包类,可以使用指定的语言环境.使用类加载器的方式加载配置文件
        String className = ResourceBundle.getBundle("party").getString("singer");
        Class c = Class.forName(className);
        return (Singer) c.newInstance();
    }

    public static Dancer findDancer() {
        return new Yangliping();
    }

    public static Speaker findSpeaker() {
        return new Zhaobenshan();
    }

    public static Actor findActor() {
        return new Liuqian();
    }

}

接口类(这里只paste了其中一个接口):

package com.xiaofan.demo;

public interface Singer {
    public void sing();
}

接口实现类(这里只paste了其中一个实现类):

package com.xiaofan.demo.impl;

import com.xiaofan.demo.Singer;

public class Zhangxueyou implements Singer {

    @Override
    public void sing() {
        System.out.println("张学友 演唱 一路有你!");
    }

}

配置文件:

singer = com.xiaofan.demo.impl.Zhangxueyou
dancer =com.xiaofan.demo.impl.Yangliping
speaker = com.xiaofan.demo.impl.Fenggong
actor =com.xiaofan.demo.impl.Liuqian

--------------------------------------------------------------------------------------------

 

反射,工厂模式

标签:

原文地址:http://www.cnblogs.com/vaer/p/4342530.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!