【问题标题】:Count occurrences of words in ArrayList [duplicate]计算 ArrayList 中单词的出现次数
【发布时间】:2011-03-06 14:58:24
【问题描述】:

我有一个 ArrayList 包含重复条目的单词。

我想计算并保存数据结构中每个单词的出现次数。

我该怎么做?

【问题讨论】:

  • 排序,迭代。或者创建一个 HashMap 遍历 arraylist 并在每次看到字符串时将计数增加一。

标签: java arraylist count


【解决方案1】:

如果您没有大量字符串,那么实现它的最短方法是使用Collections.frequency 方法,如下所示:

List<String> list = new ArrayList<String>();
list.add("aaa");
list.add("bbb");
list.add("aaa");

Set<String> unique = new HashSet<String>(list);
for (String key : unique) {
    System.out.println(key + ": " + Collections.frequency(list, key));
}

输出:

aaa: 2
bbb: 1

【讨论】:

  • 如果您想知道确切的单词频率,这很好,但对列表中的每个单词重复此操作...
  • @Yanick,是的,但您可以将 List 转换为 Set 以了解所有唯一单词
  • 好的,我已经编辑了我的帖子并添加了转换
  • @smas:这种方法既占用大量内存又效率低下。
  • @smas,找到一个词频=O(n),把一个List转成Set=O(n),从Set中寻找每个词的频率(最坏情况)=O(n) ;总和为 O(2(n^2))。虽然哈希表解决方案最多为 O(2n)
【解决方案2】:

有很多可能性。一个快速实施的解决方案可能是使用Map&lt;String, Integer&gt;,其中 String 是每个单独的单词,Integer 是每个单词的计数。

遍历列表,为它增加map中对应的值。如果还没有条目,则添加一个值为 1 的条目。

wordList = ....;

Map<String, Integer> wordCount = new HashMap<String, Integer>();

for(String word: wordList) {
  Integer count = wordCount.get(word);          
  wordCount.put(word, (count==null) ? 1 : count+1);
}

【讨论】:

  • Integer 是不可变的,您需要将其放回:wordCount.put(word, wordCount.get(word)++) - 好的,我刚刚看到你已经修好了:)
  • 已经修复,但感谢提示;)
  • 我更喜欢两遍方法 - 在第一遍中,只需将零放入地图;在第二个中,将值加一。这避免了有时令人困惑的条件逻辑,但(可能)有一些轻微的性能成本。
  • 国际海事组织“?” operator 是人们应该注意的事情,因为它被广泛使用。但你是对的,如果它会变得更复杂,最好使用两遍解决方案或使用适当的 if/else,这取决于要求。
  • 如果 Java 有一个空合并运算符 (??) 这看起来会更好
【解决方案3】:

这是一个测试驱动的类,可以做你想做的事。首先是测试:

import junit.framework.TestCase;

public class CounterTest extends TestCase {
    private Counter<String> counter;

    @Override
    protected void setUp() throws Exception {
        super.setUp();
        counter = new Counter<String>();
    }

    public void testInitialCountIsZero() throws Exception {
        assertEquals(0, counter.get("a"));
    }

    public void testCount() throws Exception {
        counter.count("a");
        assertEquals(1, counter.get("a"));
    }
}

现在上课:

import java.util.HashMap;

public class Counter<T> {
    private final HashMap<T, Integer> map = new HashMap<T, Integer>();

    public int get(T key) {
        final Integer n = map.get(key);
        return n == null ? 0 : n;
    }

    public void count(T key) {
        map.put(key, get(key) + 1);
    }
}

为了解决您的具体问题,您将创建一个计数器,并遍历您的列表,计算每个元素。

Counter<String> counter = new Counter<String>();
for (String string: myList)
    counter.count(string);

【讨论】:

    【解决方案4】:

    或者,如果您懒得自己动手(或优秀的工业程序员 :p),请使用来自 google guava 的 Multiset

    【讨论】:

      猜你喜欢
      • 2012-08-09
      • 2021-11-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-24
      • 1970-01-01
      • 2023-04-04
      相关资源
      最近更新 更多