ホームページ  >  記事  >  Java  >  Javaリフレクションを使用してオブジェクトのプロパティに値を割り当てるにはどうすればよいですか?

Javaリフレクションを使用してオブジェクトのプロパティに値を割り当てるにはどうすればよいですか?

WBOY
WBOY転載
2023-05-07 10:43:191884ブラウズ

はじめに

私は最近、将来的に複数の言語を変換するための汎用メソッドを実装するというプロジェクトで問題に遭遇しました。この要件に基づいて、リフレクションを使用して実装することにしました。属性値、以下はリフレクションを使用してオブジェクト属性値を設定する方法です。

方法 1: ここでは、Field の設定側の Field 属性が使用され、次に、可視性が設定され、次に値が設定され、最後に印刷

//変数に値を代入し、オブジェクトのフィールドに値を代入します object

f.set(object, value);

//Field クラスのインスタンスを取得した後、メソッドの 1 つを呼び出すことができます。

//メソッド: get(Object obj) 表現されたフィールドの値を返します。指定されたオブジェクト obj

package com.example.reflectiondemo;
 
import java.lang.reflect.Field;
 
/**
 * @program my-project-model
 * @description:
 * @author: lee
 * @create: 2023/01/04 19:52
 */
public class ReflectMain {
 
    private String readOnly;
 
    public String getReadOnly() {
        return readOnly;
    }
 
    public void setReadOnly(String readOnly) {
        System.out.println("set");
        this.readOnly = readOnly;
    }
 
    public static void main(String[] args) throws NoSuchFieldException, IllegalAccessException {
        ReflectMain t = new ReflectMain();
        Field f = t.getClass().getDeclaredField("readOnly");
        f.setAccessible(true);
        f.set(t, "test");
        System.out.println(t.getReadOnly());
 
    }
}

のこのフィールドによって実行されます。メソッド 2: 呼び出しメソッドを使用します。

#
package com.example.reflectiondemo;
 
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
 
/**
 * @program my-project-model
 * @description:
 * @author: lee
 * @create: 2023/01/04 19:52
 */
public class ReflectMain {
 
    private String readOnly;
 
    public String getReadOnly() {
        return readOnly;
    }
 
    public void setReadOnly(String readOnly) {
        System.out.println("set");
        this.readOnly = readOnly;
    }
 
    //    public static void main(String[] args) throws NoSuchFieldException, IllegalAccessException {
//        ReflectMain t = new ReflectMain();
//        Field f = t.getClass().getDeclaredField("readOnly");
//        f.setAccessible(true);
//        f.set(t, "test");
//        System.out.println(t.getReadOnly());
//
//    }
    public static void main(String[] args) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
        ReflectMain t = new ReflectMain();
        Method setReadOnly = t.getClass().getMethod("setReadOnly", String.class);
        String s = "test2";
        setReadOnly.invoke(t, s);
        System.out.println(t.getReadOnly());
 
    }
}

Javaリフレクションを使用してオブジェクトのプロパティに値を割り当てるにはどうすればよいですか?

リフレクションを使用すると、それぞれを簡単に設定できることがわかります。属性。プライベート属性の場合でも、属性値を簡単に設定できます。以下のデモ例を使用してみましょう。これにより、初期機能が設定されます。

概要:

つまり、最初のメソッドは、属性の set メソッドを呼び出さずに割り当てを完了します。

しかし、2 番目のメソッドは、属性の set メソッドを呼び出すことによって行われます。課題を完了するために。

したがって、プログラム内でプログラムの属性の値を変更し、追加の処理も実行したい場合は、これらの処理を set メソッドに記述し、2 番目のメソッドを使用できます

public class MultiLangContentUtil {
 
    /**
     * 从PO查询数据赋值到DTO
     * 注意!!这里的多语字段根据
     * 简体中文的变量名 英文名和繁体名需要根据规则进行 指定
     * 规则如下
     * 英文名=简体中文名2
     * 繁体名=简体中文名3
     *
     * @param targetPO        数据库中查询出的数据
     * @param targetDTO       将要转换的对象DTO
     * @param targetMultiName 需要展示的多语字段
     * @throws NoSuchFieldException
     * @throws IllegalAccessException
     */
    public static void setMultiLangDTOName(Object targetPO, Object targetDTO, String targetMultiName) {
        try {
 
            String locale = MultiLangContentUtil.getLocale();
            Class<?> targetDTOClass = targetDTO.getClass();
            Class<?> targetPOClass = targetPO.getClass();
            //这里是将targetMultiName进行展示
            Field declaredFieldDTO = targetDTOClass.getDeclaredField(targetMultiName);
            declaredFieldDTO.setAccessible(true);
            switch (locale) {
                case ZH_CN:
                    //获取PO的值
                    Field declaredFieldPO = targetPOClass.getDeclaredField(targetMultiName);
                    //获取DTO对象
                    declaredFieldPO.setAccessible(true);
                    //对DTO根据PO进行设置
                    declaredFieldDTO.set(targetDTO, declaredFieldPO.get(targetPO));
                    break;
                case EN_US:
                    //获取PO的值
                    Field declaredFieldPO2 = targetPOClass.getDeclaredField(targetMultiName + 2);
                    //获取DTO对象
                    declaredFieldPO2.setAccessible(true);
                    //对DTO根据PO进行设置
                    declaredFieldDTO.set(targetDTO, declaredFieldPO2.get(targetPO));
                    break;
                case ZH_TW:
                    //获取PO的值
                    Field declaredFieldPO3 = targetPOClass.getDeclaredField(targetMultiName + 3);
                    //获取DTO对象
                    declaredFieldPO3.setAccessible(true);
                    //对DTO根据PO进行设置
                    declaredFieldDTO.set(targetDTO, declaredFieldPO3.get(targetPO));
                    break;
                default:
                    break;
            }
            //防止没有抽取多语的情况下没有参照返回,默认情况下设置中文
            if (StringUtils.isBlank((String) declaredFieldDTO.get(targetDTO))) {
                //获取PO的值
                Field declaredFieldPO = targetPOClass.getDeclaredField(targetMultiName);
                //获取DTO对象
                declaredFieldPO.setAccessible(true);
                //对DTO根据PO进行设置
                declaredFieldDTO.set(targetDTO, declaredFieldPO.get(targetPO));
            }
        } catch (NoSuchFieldException e) {
            log.error("查询当前字段--->{}不存在{},", targetMultiName, e);
        } catch (IllegalAccessException e) {
            log.error("查询字段--->{}多语时发生非法状态异常{},", targetMultiName, e);
        } catch (Exception e) {
            log.error("查询字段{}多语时发生错误{},", targetMultiName, e);
        } catch (Throwable throwable) {
            log.error("查询多语言字段{}发生未知错误{}", targetMultiName, ThrowableUtil.stackTraceToString(throwable));
        }
    }
 
    /**
     * 更新多语字段
     *
     * @param targetDTO     需要转换的字段
     * @param targetPO      数据库PO
     * @param fieldName     多语字段
     * @param MultiLangSize 多语字段的数量
     */
    public static void updateMultiLang(Object targetDTO, Object targetPO, String fieldName, Integer MultiLangSize) {
        try {
            Class<?> targetDTOClass = targetDTO.getClass();
            Class<?> targetPOClass = targetPO.getClass();
 
            Field dtoClassField = targetDTOClass.getDeclaredField(fieldName);
            dtoClassField.setAccessible(true);
            if (StringUtils.isNotBlank((String) dtoClassField.get(targetDTO))) {
                Field poClassField = targetPOClass.getDeclaredField(fieldName);
                poClassField.setAccessible(true);
                poClassField.set(targetPO, dtoClassField.get(targetDTO));
            }
            for (int i = 2; i <= MultiLangSize; i++) {
                Field dtoClassField2 = targetDTOClass.getDeclaredField(fieldName + i);
                dtoClassField2.setAccessible(true);
                if (StringUtils.isNotBlank((String) dtoClassField2.get(targetDTO))) {
                    Field poClassField2 = targetPOClass.getDeclaredField(fieldName + i);
                    poClassField2.setAccessible(true);
                    poClassField2.set(targetPO, dtoClassField2.get(targetDTO));
                }
            }
        } catch (NoSuchFieldException e) {
            log.error("更新当前字段--->{}不存在{},", fieldName, e);
        } catch (IllegalAccessException e) {
            log.error("更新字段--->{}多语时发生非法状态异常{},", fieldName, e);
        } catch (Exception e) {
            log.error("更新字段{}多语时发生错误{},", fieldName, e);
        } catch (Throwable throwable) {
            log.error("更新多语言字段{}发生未知错误{}", fieldName, ThrowableUtil.stackTraceToString(throwable));
        }
    }
 
    /**
     * 获取本地的语言,默认中文
     * en_US  英文
     * zh_CN  简体中文
     * zh_TW  繁体中文
     *
     * @return
     */
    public static final String getLocale() {
        String locale = InvocationInfoProxy.getLocale();
        return StringUtils.isEmpty(locale) ? "zh_CN" : locale;
    }
}

このツール クラスの中心となるアイデアは次のとおりです。

  • フィールドの get メソッドを使用して属性値を取得します

  • フィールドの set メソッドを使用して属性を設定します

//変数に値を代入し、オブジェクトのフィールドに値を代入する object

f.set(object, value);

//Field クラスのインスタンスを取得します。その後、メソッド

//メソッドを呼び出すことができます。get(Object obj) は、指定されたオブジェクト obj

のこの Field によって表されるフィールドの値を返します。

以上がJavaリフレクションを使用してオブジェクトのプロパティに値を割り当てるにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はyisu.comで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。