web-dev-qa-db-ja.com

javaの変更不可能なリスト

Listを変更不可に設定しようとしています。

私のコードには、リストを返すメソッドがあります。

このリストは変更すべきではありませんが、unmodifiableListによって返される例外をキャッチしたくありません。

private List<T> listeReferenceSelectAll = null;
List<T> oListeRet = new ArrayList<T>();
oListeRet = listeReferenceSelectAll;
return new ArrayList<T>(oListeRet);

これは既存のコードであり、変更できないリストを返すように変換する必要がありますが、「add」メソッドが呼び出された場合、例外をキャッチする必要はありません。

まず、例外をログに記録してキャッチしないように「add」メソッドをオーバーライドするためにListを実装するクラスを作成しました。

しかし、それを正しくインスタンス化する方法がわかりません...

12
user2346325

これを絶対に行う必要がある場合は、作成するリストのJava.util.Listで指定された規約に従ってください。

あなたのコードは次のようになります

public class UnmodifiableArrayList<E>  extends ArrayList<E> {

    public UnmodifiableArrayList(Collection<? extends E> c) {
        super(c);
    }

    public boolean add(int index) {
        return false;//Returning false as the element cannot be added 
    }

    public boolean addAll(Collection<? extends E> c) {
        return false;//Returning false as the element cannot be added 
    }

    public E remove(int index) {
        return null;//Returning null as the element cannot be removed
    }
}

同じ行に必要なメソッドを追加します。ただコードの変更に使用される可能性のあるすべてのコンストラクターとメソッドがオーバーライドされることを確認してください。これにより、リストが変更不可になるようにします。

Collections APIを使用する方がよりクリーンで優れた方法です。Collections.UnmodifiableListを使用してもニーズが満たされない場合にのみ、この方法を使用してください。

デバッグ中はこれが悪夢になるので、できるだけログに記録してください。

4
Aditya

Java.util.Collectionsが必要です:

return Collections.unmodifiableList(oListeRet);

独自に記述する必要がある場合は、そのクラスにListインターフェースを実装させ、内容を変更するメソッドの例外をスローさせます。

61
duffymo

Collections.unmodifiableList

指定されたリストの変更不可能なビューを返します。このメソッドにより、モジュールはユーザーに内部リストへの「読み取り専用」アクセスを提供できます。返されたリストのクエリ操作は、指定されたリストに「読み取り」され、返されたリストを直接または反復子を介して変更しようとすると、UnsupportedOperationExceptionが発生します。指定されたリストがシリアル化可能である場合、返されるリストはシリアル化可能です。同様に、返されたリストは、指定されたリストが実装している場合、RandomAccessを実装します。

18
Achintya Jha

Java-9は、作成する新しいメソッドを提供します nmodifiable/immutableList

jshell> List<Integer> list = List.of(1,2,3);
list ==> [1, 2, 3]

jshell> list.add(10);
|  Java.lang.UnsupportedOperationException thrown: 
|        at ImmutableCollections.uoe (ImmutableCollections.Java:70)
|        at ImmutableCollections$AbstractImmutableList.add (ImmutableCollections.Java:76)
|        at (#6:1)

List.of は、任意の数の要素を含む不変のリストを作成します。

6
Anton Balaniuc

受け入れられた回答はUnsupportedOperationExceptionの省略/飲み込みの要求に対応していますが、それが望ましくない慣行である理由を説明する必要があります。

1)例外を飲み込むという全体的な意図は、「フェイルファスト」原理の矛盾です。欠陥を早期に発見して捕らえる代わりに、彼らは「じゅうたんの下」に行って時限爆弾に変えられるだけです。

2)UnsupportedOperationExceptionをスローしないのは、Listの契約に直接違反することです。

Throws:
    UnsupportedOperationException - if the add method is not supported by this list.

したがって、質問のタイトル「Javaでの変更不可能なリスト」に書かれていることに対する正しい答えは、次のようになります。

return Collections.unmodifiableList(oListeRet);
5
Alexey Dmitriev

変更不可能なリストに関するコメントは正しいです。 Collections.unmodifiableListを呼び出すメソッドアクセサーを作成します。ただし、配列をそのまま使用し、内部的にリストを使用することもできます。

 public MyObject[] getObjects() {
    return (MyObject[]) mList.toArray();
 }
0
Joel Teply

1)これらの行は意味がありません

List<T> oListeRet = new ArrayList<T>();
oListeRet = listeReferenceSelectAll;

2)Collections.unmodifiableListを使用します。

return Collections.unmodifiableList(oListeRet);

スローする可能性のある例外をキャッチする必要はありません。これらはすべてUnsupportedOperationException-RuntimeExceptionsです。

0