マップオブジェクトを変更可能なライブラリからいくつかのJavaオブジェクトを取得しています。 Collections.unmodifiableMap()メソッドでマップオブジェクトをラップすることによって、実行時にのみこれらのオブジェクトフィールドを読み取る方法が必要です。私はJavaのリフレクションAPIを使用して、以下のアプローチを試してみましたが、私は、フィールドからの実際のマップのインスタンスを得ることで立ち往生しています:リフレクションを使用して実行時にJava Beanの可変フィールドを変更不能にする方法
public static <T>T freeze(T obj){
if(obj!=null){
Field[] fields=obj.getClass().getDeclaredFields();
for(Field field:fields){
if(field.getType().equals(Map.class)){
//How to wrap a Map instance from the field in Collections.unmodifiableMap() object
}
}
}
return obj;
}
EDIT --------------- -------------------------------------------------- -------------------------------------------------- ---------- 私はjava.util.Dateオブジェクトをラップし、すべての変更可能な操作を無効にするImmutable Dateクラスを作成しました。このラッパーを使用して、私はCollections.unmodifiableCollection()と同様の機能を得ることができます。
final class DateUtil{
private DateUtil(){}
/**
*
* @param date
* @return Date
*
* This method will return an unmodifiable Date object.
*
*/
public static Date unmodifiableDate(Date date){
if(date==null){
throw new IllegalArgumentException();
}
return new ImmutableDate(new Date(date.getTime()));
}
/**
* This Date sub-class will override all the mutable Date operations
* and throw UnsupportedOperationException.
*/
private final static class ImmutableDate extends Date{
private static final long serialVersionUID = -1869574656923004097L;
private final Date date;
ImmutableDate(Date date){
this.date=date;
}
@Override
public void setTime(long date) {
throw new UnsupportedOperationException();
}
@Override
public void setDate(int date) {
throw new UnsupportedOperationException();
}
@Override
public void setHours(int hours) {
throw new UnsupportedOperationException();
}
@Override
public void setMinutes(int minutes) {
throw new UnsupportedOperationException();
}
@Override
public void setSeconds(int seconds) {
throw new UnsupportedOperationException();
}
@Override
public void setYear(int year) {
throw new UnsupportedOperationException();
}
@Override
public void setMonth(int month) {
throw new UnsupportedOperationException();
}
@Override
public Object clone() {
throw new UnsupportedOperationException();
}
}
}
ありがとうございます!このメソッドを呼び出した後にキーを変更/追加しようとすると、java.lang.UnsupportedOperationExceptionがスローされる –
java.util.Dateフィールドでこれを行うことは可能ですか?また、フィールドを最終的に動的にすることもできますか? –
ああ、残念ながら、Javaではjava.util.Dateの不変型はありません。Collections.unmodifiableMapはjava.util.Mapクラス用です(私が知る限り)。 'final'はコンパイル時の言語機能であり、ソースコード内の変数の再割り当てを防ぐので、最終的な修飾子がこの場合に役立つかどうかはわかりません。実行時には(ほとんど)何もしません。しかし、興味深い問題があります:)私は研究を行い、もし私が何かを見つけたら私はあなたと分かち合うでしょう。 – Elka