カスタムオブジェクトのArrayListが2つあります。両方のArrayListから重複するエントリを削除したいと思います。
オブジェクトには、fName、lName、およびidの3つのフィールドがあります。idが複数回出現する場合は、両方のリストから削除したいと思います。
どうやってやるの?
両方のリストをマージし、2つの重複するエントリも削除しても問題ありません。
マージする場合:両方のリストのコンテンツをマップにコピーするだけです。その後、重複はもうありません(ただし、実際の注文は失われます)。
Map<Integer, MyObject> temp = new HashMap<Integer, MyObject>();
for (MyObject obj:firstList) {
temp.put(obj.getId(), obj);
}
for (MyObject obj:secondList) {
temp.put(obj.getId(), obj);
}
List<MyObject> result = new ArrayList<MyObject>(temp.values());
equals
クラスにandメソッドが正しく実装されている場合はhashCode
、リストをaに変換しHashSet
て、重複を排除します。HashSet<T>
コンストラクターはaを受け入れるので、Collection<T>
うまくいくはずです。
カスタムコンパレータ関数(この場合はのみを比較するものなどid
)が必要な場合は、を作成するときにカスタムComparator<T>
実装を渡しTreeSet
ます。要約すると、両方のオブジェクトのsを比較するコンパレータを作成し、コンストラクタid
に渡します。TreeSet
次に、両方のリストからこのセットにアイテムを追加すると、重複を排除できます。何かのようなもの:
public class Test {
public static void main(String[] args) {
Person p1 = new Person("first", "id1");
Person p2 = new Person("dummy", "id1"); // same id as above
Person p3 = new Person("second", "id2");
Person p4 = new Person("third", "id1");
List<Person> asList = Arrays.asList(p1, p2, p3, p4);
CustomComparator comparator = new CustomComparator();
TreeSet<Person> ts = new TreeSet<Person>(comparator);
TreeSet<Person> duplicates = new TreeSet<Person>(comparator);
for (Person p : asList) {
if (ts.contains(p) || duplicates.contains(p)) {
duplicates.add(p);
ts.remove(p);
} else {
ts.add(p);
}
}
System.out.println(ts);
}
}
class Person {
public Person(String name, String id) {
super();
this.name = name;
this.id = id;
}
public String name;
public String id;
@Override
public String toString() {
StringBuilder builder = new StringBuilder();
builder.append("Person [id=");
builder.append(id);
builder.append(", name=");
builder.append(name);
builder.append("]");
return builder.toString();
}
}
class CustomComparator implements Comparator<Person> {
@Override
public int compare(Person o1, Person o2) {
return o1.id.compareTo(o2.id);
}
}
この目的にはセットを使用します。
注:可変オブジェクトをセット要素として使用する場合は、細心の注意を払う必要があります。オブジェクトがセット内の要素であるときに、等しい比較に影響を与える方法でオブジェクトの値が変更された場合、セットの動作は指定されません。この禁止の特殊なケースは、セットがそれ自体を要素として含むことは許可されないということです。
HashSet<Integer> list_1_ids = new HashSet<Integer>();
HashSet<Integer> list_2_ids = new HashSet<Integer>();
for (CustomObject x : list1) list_1_ids.add(x.id);
for (CustomObject x : list2) list_2_ids.add(x.id);
HashSet<Integer> both_ids = list_1_ids;
both_ids.retainAll(list_2_ids);
List<CustomObject> pruned_list_1 = new ArrayList<CustomObject>();
for (CustomObject x : list1) if (!both_ids.contains(x.id)) pruned_list_1.add(x);
List<CustomObject> pruned_list_2 = new ArrayList<CustomObject>();
for (CustomObject x : list2) if (!both_ids.contains(x.id)) pruned_list_2.add(x);