JavaでList内の重複データを除外する場合は通常HashSetやTreeSetへ追加する事でList内のデータを一意にする事が出来ます。
但しListの型が配列になっている場合、この方法では重複データは一意にする事が出来ません。
List< 配列型>の重複データを除外する場合の失敗例
失敗例のサンプルソース
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
List<String[]> list = new ArrayList<String[]>(); String[] str1 = {"a", "b" ,"c", "d", "e"}; String[] str2 = {"b", "b" ,"c", "d", "e"}; String[] str3 = {"a", "b" ,"c", "d", "d"}; String[] str4 = {"v", "w" ,"x", "y", "z"}; String[] str5 = {"a", "b" ,"c", "d", "e"}; String[] str6 = {"v", "w" ,"x", "y", "z"}; list.add(str1); list.add(str2); list.add(str3); list.add(str4); list.add(str5); list.add(str6); Set<String[]> set = new HashSet<String[]>(); for(String[] array : list) { set.add(array); } Iterator<String[]> ite = set.iterator(); while(ite.hasNext()) { String[] array = (String[]) ite.next(); StringBuffer buf = new StringBuffer(); for (int i = 0; i < array.length; i++) { buf.append(array[i] + ","); } System.out.println(buf.toString()); } |
コンソール
a,b,c,d,d,
v,w,x,y,z,
v,w,x,y,z,
a,b,c,d,e,
b,b,c,d,e,
a,b,c,d,e,
上記サンプルソースでのコンソールにはListへ登録した配列データ全てが重複分も含めてHashSetに登録されている事がわかります。
こういうListの型が配列になっている場合に上手く重複データを除外するプログラムを考えてみました。
Javaソース
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
/** * <p>[概 要] List<配列型>の重複配列削除処理</p> * <p>[詳 細] List内の配列に同じ配列があれば削除します。</p> * <p>[備 考] </p> * @param listArray<配列型> * @return 重複データ除外後のList型オブジェクト */ public static List<String[]> overlapExcepArray(List<String[]> listArray){ // List内の配列データを連結してキーにしてMapへ登録 Map<String, String[]> map = new HashMap<String, String[]>(); for(String[] data : listArray){ // 配列内のデータを連結してMap用のキーを生成 StringBuffer buf = new StringBuffer(); for (int i = 0; i < data.length; i++) { buf.append(data[i]); } String key = buf.toString(); // 重複データを除外してMapへ登録 if(!map.containsKey(key)) { map.put(key, data); } } // Mapへ登録した値をListへ変換 List<String[]> uniqueList = new ArrayList<String[]>(map.values()); return uniqueList; } |
JUnitサンプル
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 |
@Test public void overlapExcepArrayTest() { // 準備 List<String[]> paramList = new ArrayList<String[]>(); String[] str1 = {"a", "b" ,"c", "d", "e"}; String[] str2 = {"b", "b" ,"c", "d", "e"}; String[] str3 = {"a", "b" ,"c", "d", "d"}; String[] str4 = {"v", "w" ,"x", "y", "z"}; String[] str5 = {"a", "b" ,"c", "d", "e"}; String[] str6 = {"v", "w" ,"x", "y", "z"}; paramList.add(str1); paramList.add(str2); paramList.add(str3); paramList.add(str4); paramList.add(str5); paramList.add(str6); List<String[]> expected = new ArrayList<String[]>(); expected.add(str2); expected.add(str4); expected.add(str3); expected.add(str1); // 実行 List<String[]> result = UtilSample1.overlapExcepArray(paramList); // 検証 assertEquals("Listの件数が一致していません。", expected.size(), result.size()); for (int i = 0; i < expected.size(); i++) { assertArrayEquals("配列データが一致していません。", expected.get(i), result.get(i)); } } |