ArrayList with Objects,查找重复的 object 字段
ArrayList with Objects, find duplicate object fields
如标题所说,我在 java 和 Objects 中有一个 ArrayList。 Objects基本上是酒店的房型。它们都有类型名称、床位数量等。现在我的问题是,我需要找到两个 objects 类型名称字段具有相同的值。我用 for 循环遍历列表,但不知道如何继续。这是我的代码:
import java.util.ArrayList;
public class KamerType {
private String typeNaam;
private int aantalBedden;
private double prijsPerNacht;
public KamerType(String tN, int aB, double pPN){
typeNaam = tN;
aantalBedden = aB;
prijsPerNacht = pPN;
}
public String toString(){
String s = "De kamer van type " + typeNaam + " heeft " + aantalBedden + " bedden en kost " + prijsPerNacht + " euro.";
return s;
}
public static void main(String a[]){
ArrayList<KamerType> kamertypes = new ArrayList<KamerType>();
KamerType k1 = new KamerType("Standaard", 2, 60.0);
kamertypes.add(k1);
KamerType k2 = new KamerType("DeLuxe", 2, 85.0);
kamertypes.add(k2);
KamerType k3 = new KamerType("DeLuxe", 4, 125.0);
kamertypes.add(k3);
KamerType k4 = new KamerType("Hiker", 2, 35.0);
kamertypes.add(k4);
System.out.println("Dit zijn de kamertypen:");
for(KamerType KT : kamertypes){
System.out.println(KT.toString());
}
System.out.println("\nTesten op zelfde typenaam:");
for(KamerType KT : kamertypes){
/*if(kamertypes.get(1).typeNaam == KT.typeNaam){
???
}*/
}
} // end of main
}// end of class
感谢任何帮助:)
编辑:npinti 和 Djorde Ivanovic 给出了两个可行的答案,npinti 给出了更多 guideline-ish 的答案。非常感谢你们:)
要比较字符串,请使用 'equals' 函数而不是 '=='
像这样
if(kamertypes.get(1).typeNaam.equals(KT.typeNaam))
首先为您的字段创建一个 getter 方法:
public String getTypeNaam() {
return typeNaam;
}
然后你可以比较两个值:
if(kt1.getTypeNaam().equals(kt2.getTypeNaam)) {
// Name of kt1 and kt2 is identical
}
如果要比较每个对象,请使用嵌套循环:
for(KamerType kt1 : kamertypes){
for(KamerType kt2 : kamertypes) {
if(kt1.getTypeNaam().equals(kt2.getTypeNaam)) {
// Name of kt1 and kt2 is identical
}
}
}
请注意,这也会找到两个相同的对象,因为它们当然具有相同的名称。您可以通过将条件 kt1 != k2
添加到 if
.
来排除这些条件
由于这听起来像是家庭作业,我将尝试提供一些基本的指导方针而不是解决方案。
最基本(尽管效率较低)的方法是进行嵌套循环并比较房间:
(我假设如果 object 的所有 3 个字段都相同,那么我引用的是相同的 object。因此,这部分:AND (r1.aantalBedden != r2.aantalBedden)) AND (r1.prijsPerNacht != r2.prijsPerNacht)
会有所帮助我避免说我有一个副本(比较相同的 object)。
for each KamerType r1 in kamertypes
for each KamerType r2 in kamertypes
if(((r1.typeNaam.equals(r2.typeNaam)) AND (r1.aantalBedden != r2.aantalBedden)) AND (r1.prijsPerNacht != r2.prijsPerNacht))
print("We have duplicates");
另一种更标准(如果你愿意)的方法是:
使您的 KamerType
class 覆盖 equals
方法,并将其更改为两个 KamerType
object如果它们具有相同的 typeNaam
字段,则相同。
使用数据结构,例如 Set
(不允许重复)并将您的 KamerType
object 放入其中。这将在内部调用 equals
方法,如果它产生 true
,那么它会点头将房间添加到集合中,从而允许您以 KamerType
object 是唯一的。
顺便说一句,我在您的代码中也注意到了这一点:if(kamertypes.get(1).typeNaam == KT.typeNaam)
。在Java中,字符串比较是通过equals
方法完成的,所以应该变成if(kamertypes.get(1).typeNaam.equals(KT.typeNaam))
.
编辑:根据您的评论,第二种方法可以让您通过遍历列表一次来解决问题。还有第三种方法可以解决这个问题,但我认为这是我上面提供的两种解决方案中最糟糕的部分(实施起来稍微复杂,执行时间可能更长)。
使您的 KamerType
class 实现 Comparable
接口。这将迫使您实施 compareTo()
* 方法。在您的实施中,您只需(至少在本例中)比较 typeNaam
。然后对列表进行排序。
获得排序后的列表后,从列表的第二个元素开始并将其与前一个元素进行比较。由于您的列表按 typeNaam
排序,任何两个具有相同 typeNaam
字段的 object 将在您的列表中彼此紧挨着,因此您无需查找重复项具有 O^2
时间复杂度。
- 这将允许您调用
Collections.sort()
并使其以您想要的方式对您的 collection 进行排序。
这是您需要的。首先为您的私有字段添加 getter。我使用 i 和 j 循环来避免重复。
for(int j = 0;j<kamertypes.size();j++){
for(int i = j+1;i<kamertypes.size();i++){
if(kamertypes.get(j).getTypeNaam().equals(kamertypes.get(i).getTypeNaam()) && i!=j){
System.out.println(kamertypes.get(j) + " and " +kamertypes.get(i));
}
}
}
如标题所说,我在 java 和 Objects 中有一个 ArrayList。 Objects基本上是酒店的房型。它们都有类型名称、床位数量等。现在我的问题是,我需要找到两个 objects 类型名称字段具有相同的值。我用 for 循环遍历列表,但不知道如何继续。这是我的代码:
import java.util.ArrayList;
public class KamerType {
private String typeNaam;
private int aantalBedden;
private double prijsPerNacht;
public KamerType(String tN, int aB, double pPN){
typeNaam = tN;
aantalBedden = aB;
prijsPerNacht = pPN;
}
public String toString(){
String s = "De kamer van type " + typeNaam + " heeft " + aantalBedden + " bedden en kost " + prijsPerNacht + " euro.";
return s;
}
public static void main(String a[]){
ArrayList<KamerType> kamertypes = new ArrayList<KamerType>();
KamerType k1 = new KamerType("Standaard", 2, 60.0);
kamertypes.add(k1);
KamerType k2 = new KamerType("DeLuxe", 2, 85.0);
kamertypes.add(k2);
KamerType k3 = new KamerType("DeLuxe", 4, 125.0);
kamertypes.add(k3);
KamerType k4 = new KamerType("Hiker", 2, 35.0);
kamertypes.add(k4);
System.out.println("Dit zijn de kamertypen:");
for(KamerType KT : kamertypes){
System.out.println(KT.toString());
}
System.out.println("\nTesten op zelfde typenaam:");
for(KamerType KT : kamertypes){
/*if(kamertypes.get(1).typeNaam == KT.typeNaam){
???
}*/
}
} // end of main
}// end of class
感谢任何帮助:)
编辑:npinti 和 Djorde Ivanovic 给出了两个可行的答案,npinti 给出了更多 guideline-ish 的答案。非常感谢你们:)
要比较字符串,请使用 'equals' 函数而不是 '=='
像这样
if(kamertypes.get(1).typeNaam.equals(KT.typeNaam))
首先为您的字段创建一个 getter 方法:
public String getTypeNaam() {
return typeNaam;
}
然后你可以比较两个值:
if(kt1.getTypeNaam().equals(kt2.getTypeNaam)) {
// Name of kt1 and kt2 is identical
}
如果要比较每个对象,请使用嵌套循环:
for(KamerType kt1 : kamertypes){
for(KamerType kt2 : kamertypes) {
if(kt1.getTypeNaam().equals(kt2.getTypeNaam)) {
// Name of kt1 and kt2 is identical
}
}
}
请注意,这也会找到两个相同的对象,因为它们当然具有相同的名称。您可以通过将条件 kt1 != k2
添加到 if
.
由于这听起来像是家庭作业,我将尝试提供一些基本的指导方针而不是解决方案。
最基本(尽管效率较低)的方法是进行嵌套循环并比较房间:
(我假设如果 object 的所有 3 个字段都相同,那么我引用的是相同的 object。因此,这部分:AND (r1.aantalBedden != r2.aantalBedden)) AND (r1.prijsPerNacht != r2.prijsPerNacht)
会有所帮助我避免说我有一个副本(比较相同的 object)。
for each KamerType r1 in kamertypes
for each KamerType r2 in kamertypes
if(((r1.typeNaam.equals(r2.typeNaam)) AND (r1.aantalBedden != r2.aantalBedden)) AND (r1.prijsPerNacht != r2.prijsPerNacht))
print("We have duplicates");
另一种更标准(如果你愿意)的方法是:
使您的
KamerType
class 覆盖equals
方法,并将其更改为两个KamerType
object如果它们具有相同的typeNaam
字段,则相同。使用数据结构,例如
Set
(不允许重复)并将您的KamerType
object 放入其中。这将在内部调用equals
方法,如果它产生true
,那么它会点头将房间添加到集合中,从而允许您以KamerType
object 是唯一的。
顺便说一句,我在您的代码中也注意到了这一点:if(kamertypes.get(1).typeNaam == KT.typeNaam)
。在Java中,字符串比较是通过equals
方法完成的,所以应该变成if(kamertypes.get(1).typeNaam.equals(KT.typeNaam))
.
编辑:根据您的评论,第二种方法可以让您通过遍历列表一次来解决问题。还有第三种方法可以解决这个问题,但我认为这是我上面提供的两种解决方案中最糟糕的部分(实施起来稍微复杂,执行时间可能更长)。
使您的
KamerType
class 实现Comparable
接口。这将迫使您实施compareTo()
* 方法。在您的实施中,您只需(至少在本例中)比较typeNaam
。然后对列表进行排序。获得排序后的列表后,从列表的第二个元素开始并将其与前一个元素进行比较。由于您的列表按
typeNaam
排序,任何两个具有相同typeNaam
字段的 object 将在您的列表中彼此紧挨着,因此您无需查找重复项具有O^2
时间复杂度。- 这将允许您调用
Collections.sort()
并使其以您想要的方式对您的 collection 进行排序。
- 这将允许您调用
这是您需要的。首先为您的私有字段添加 getter。我使用 i 和 j 循环来避免重复。
for(int j = 0;j<kamertypes.size();j++){
for(int i = j+1;i<kamertypes.size();i++){
if(kamertypes.get(j).getTypeNaam().equals(kamertypes.get(i).getTypeNaam()) && i!=j){
System.out.println(kamertypes.get(j) + " and " +kamertypes.get(i));
}
}
}