繁体   English   中英

Java删除2个ArrayList对象之间的公共元素

[英]Java Remove common elements between 2 ArrayList of objects

我有一个Java类

class Students{
    private String fName;   
    private String lName;
    private String uName;


    public Students(String fName, String lName, String uName) {
            this.fName = fName;
            this.lName = lName;
            this.uName = uName;
     }      

    public String getuName() {
        return uName;
    }
    public void setuName(String uName) {
        this.uName = uName;
    }
    public String getfName() {
        return fName;
    }
    public void setfName(String fName) {
        this.fName = fName;
    }
    public String getlName() {
        return lName;
    }
    public void setlName(String lName) {
        this.lName = lName;
    }

}

我也用这个

public class TestClass {
public static void main(String[] args) {

    Students students1 = new Students("xyz","abc","xyzAbc");
    Students students2 = new Students("poi","son","poison");
    Students students3 = new Students("yog","jos","yogjos");

    Students students4 = new Students("xyz","abc","xyzAbc");
    Students students5 = new Students("pon","son","xyzAbc");
    Students students6 = new Students("yog","jos","someotherUName");
    Students students7 = new Students("yog","jos","someotherUName2");

    List studentList1 = new ArrayList();
    List studentList2 = new ArrayList();

    studentList1.add(students1);
    studentList1.add(students2);
    studentList1.add(students3);

    studentList2.add(students4);
    studentList2.add(students5);
    studentList2.add(students6);
}
}

现在,我需要一个仅包含唯一的“ uName”值的过滤列表。 因此,我希望每个列表的“ uName”字段之间进行比较,并删除常见的列表。

最后,我需要2个过滤器列表,分别用于StudentList1和StudentList2。

我读到有关removeAll方法的信息,但它似乎适用于整数/字符串数据列表,而不适用于对象列表(如我的情况)。

请提出建议。

您可以设置列表,然后(如果需要)将其取回:

new ArrayList(new HashSet<String>(list))创建仅包含源列表中唯一元素的列表。

1.如果您希望每个列表中具有独特的 uName值,那么你可以使用TreeSetjava.util.Collection接口一起Comparator ,从java.util.Comparator

2.如果要合并两个列表并具有唯一的uName ,请合并两个列表,然后使用TreeSetComparator

3. Comparator提供了多种方式进行比较灵活性 ...

如果List的对象正确实现equals()则仍可以使用removeAll

AbstractCollection是大多数List实现(包括ArrayList contains()它在removeAll实现中使用contains() ArrayList contains实现依赖于indexOf() ,后者最后使用equals()

您可以在Student类中实现equals() ,以在只有uName字段相等的情况下,指定Student等于另一个Student

请注意, equals具有关联的语义(请参阅其javadoc ),并且在选择实现方式时应该小心。 考虑两个学生实例在uName相等时是否真的代表同一学生。 在我看来,这听起来像是对如何整理这些东西的非常具体的要求,并且不应影响类的语义。

使用@AlexR@KumarVivekMitra的方法会更好。

首先,您应该输入列表:

List<Students> studentList1 = new ArrayList<Students>();

其次,在Students类上实现都委托给uName hashCode()equals()

public boolean equals(Object o) {
    return o instanceof Students && ((Students)o).uName.equals(uName);
}

public int hashCode() {
    return uName.hashCode();
}

现在removeAll()可以正常工作。


另一个选择是使用Set ,它仅允许由equals()方法确定的唯一值。 如果将上述方法添加到类中,则可以执行以下操作:

Set<Students> students = new HashSet<Students>();

然后将您喜欢的内容添加到其中,将永远只有唯一的uName学生。


顺便说一句,您应该以单数形式命名您的班级,即“ Student而不是“ Students

您也可以尝试使用apache commons CollectionUtils.disjunction (链接: http : //commons.apache.org/collections/apidocs/org/apache/commons/collections/CollectionUtils.html#disjunction (java.util.Collection,java.util.Collection))

您的班级Student应该重写方法hashcodeequals ,以便您的对象按名称可以是唯一的。 在这里,您可以阅读操作方法。

还要注意,某些集合中维护的所有对象都应覆盖这些方法,因此您始终知道如何比较它们。

在下一步中,您可以使用removeAll方法或带有Set的解决方案,这取决于您:-)

设置例子

List<String> list = new ArrayList(new HashSet<String>(studentList)); //这是您的唯一列表

或者,您可以使用自定义比较器而不是覆盖哈希码和等于,但是如果您希望学生始终是唯一的,则应覆盖它们

完整的可行解决方案如下。

Class Student{


.....
......
.....

   public boolean equals(Object o) {
       return o instanceof Students && ((Students)o).uName.equals(uName);
   }

   public int hashCode() {
       return uName.hashCode();
   }




}


Set studentList1 = new hashSet();
Set studentList2 = new hashSet();

将您的元素放在这些集合中。

另外,如果您想在两个集合中使用唯一的不匹配元素。 然后写如下。

studentList1.removeAll(studentList2 );

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM