从下面的列表中,我只需要“哇”和“退出”。
List<String> list = new ArrayList();
list.add("test");
list.add("test");
list.add("wow");
list.add("quit");
list.add("tree");
list.add("tree");
从下面的列表中,我只需要“哇”和“退出”。
List<String> list = new ArrayList();
list.add("test");
list.add("test");
list.add("wow");
list.add("quit");
list.add("tree");
list.add("tree");
您可以检查 Collection 中某个元素的频率,并排除频率高于 1 的元素。
List<String> list = new ArrayList<String>();
list.add("test");
list.add("test");
list.add("wow");
list.add("quit");
list.add("tree");
list.add("tree");
for(String s: list){
if(Collections.frequency(list, s) == 1){
System.out.println(s);
}
输出:
wow
quit
此代码段应为您留下一个集合 ( output
),其中仅包含列表的非重复元素。
HashSet<String> temp = new HashSet<String>();
HashSet<String> output = new HashSet<String>();
for (String element : list)
{
if (temp.contains(element)) output.remove(element);
else
{
temp.insert(element);
output.insert(element);
}
}
在 O(n*log(n)) 时间内运行:对列表中的 n 个元素中的每一个元素进行一组对数运算(设置查找、插入等)。
您可以使用 HashMap impl 来计算出现次数并仅选择出现一次的次数。
例如
void check(List<String> list)
{
Map<String,Integer> checker = new HashMap<String,Integer>();
List<String> result = new ArrayList<String>();
for(String value: list)
{
Integer count = checker.get(value);
if (count==null)
{
count = 0;
}
checker.put(value, ++count);
}
// now select only values with count == 1
for(String value: checker.keySet())
{
if (checker.get(value) == 1)
{
result.add(value);
}
}
System.out.println(result);
}
第三种方式
List result = new ArrayList();
for(Object o : list){
if(list.indexOf(o) == list.lastIndexOf(o))
result.add(o);
}
这是一种没有流的 Java 8 方式:
Map<String, Long> counts = new HashMap<>();
list.forEach(word -> counts.merge(word, 1L, Long::sum));
counts.values().removeIf(count -> count > 1);
这首先迭代列表并将每个单词的频率存储在counts
地图中。为此,我使用的Map.merge
方法是将提供的值(1L
在本例中)与给定的键(word
此处)相关联,或者使用提供的合并函数(Long::sum
)将现有值与给定的值组合。
然后,通过该方法1
从地图中删除频率大于 的单词。Collection.removeIf
整个过程具有O(n)
时间复杂度。
List aList = Arrays.asList("test", "test", "wow", "wow", "wow");
设置 hashSet = new HashSet(aList);
hashSet.addAll(aList);
现在您可以打印 HashSet 删除的所有重复值
@ROMANIA_Engineer 的解决方案应该可以正常工作,但它确实隐藏了 O(n 2 ) 复杂性,因为它Collections.frequency
是 O(n) 操作。
仍然可以压缩到单个语句中的更有效的解决方案可能是计算每个项目出现的次数并仅过滤出现一次的项目:
list.stream()
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting()))
.entrySet()
.stream()
.filter(e -> e.getValue() == 1L)
.map(Map.Entry::getKey)
.forEach(System.out::println);
如果您愿意使用第三方库,则以下内容可以与Eclipse Collections一起使用:
List<String> list = Arrays.asList("test", "test", "wow", "quit", "tree", "tree");
Set<String> set = Bags.mutable.withAll(list).selectUnique();
System.out.println(set);
输出:
[wow, quit]
您也可以Bag
直接构造 a 而不是创建 a List
,如下所示:
MutableBag<String> bag =
Bags.mutable.with("test", "test", "wow", "quit", "tree", "tree");
MutableSet<String> set = bag.selectUnique();
注意:我是 Eclipse Collections 的提交者
Java 8+
list.stream() // Stream
.filter(i -> Collections.frequency(list, i) == 1) // Stream
.collect(Collectors.toList()) // List
.forEach(System.out::println); // void
它打印该列表中仅出现一次的每个元素。
细节: