比较两个相似单词的字符串列表和测量出现单词的频率 - JAVA

时间:2013-01-09 15:35:09

标签: java arraylist hashset

我意识到我在这里一次问两个单独的问题,但我认为它们是相关的(即使只是略微)。 无论如何,我想要做的是比较Strings的两个列表(不一定是Java列表)并删除两个列表中出现的单词。我正在考虑使用ArrayListHashSetHashSet被赞成,因为列表没有被排序但我的HashSet问题是我读过他们没有允许重复。这与我的其他要求略有冲突,因为我希望能够计算每个单词出现的次数,但只显示一次......如果这有意义的话。 想想一下WordCloud的例子。

以下是我目前的情况,将两个文本文件的内容保存到两个ArrayList

ArrayList<String> words = new ArrayList<String>();
        File file = new File(fileName);
        Scanner scanner = new Scanner(file).useDelimiter("$");
        while(scanner.hasNext())
        {               
            String wrd = scanner.nextLine();
            words.add(wrd);
        }

由于两个文本文件的结构不同,我不得不使用两种不同的方法来保存数据

ArrayList<String> webWords = new ArrayList<String>();
    File webFile = new File(webFileName);
    BufferedReader br = new BufferedReader(new FileReader(webFileName));
    String testLine = "", str = "";
    int count = 0;
    String s;
    while ((testLine = br.readLine()) != null) {
            str += testLine + " ";
    }
    StringTokenizer st = new StringTokenizer(str);
    while (st.hasMoreTokens()) {
            s = st.nextToken();
            webWords.add(s);
            count++;
    }

现在我可以轻松地以类似的方式创建两个HashSet,但我现在正在使用ArrayList,因为它允许重复,我仍然不确定哪个最适合我的需要。

我需要将第二个列表与第一个列表进行比较,并删除第一个列表中出现的第二个列表中的所有单词。

我的第二个问题是试图确定(在我删除常用词之后)哪些词最常出现。

非常感谢任何帮助或指示。

3 个答案:

答案 0 :(得分:3)

如果我理解了正确的要求,那么我们可以使用HashMap<String, Integer>并将list1中的所有单词作为键放入其中,这样我们就可以避免重复了

for(String w : list1) {
      map.put(w, 0);
}

然后我们可以遍历地图条目,计算单词频率并将其作为条目值

for(Entry<String, Integer> e : map.entrySet) {
      int n = Collections.frequency(list2, e.getKey());
      e.setValue(n);
}

更新:“我希望能够删除list1中出现的list2中的单词。然后遍历list2中的剩余单词以找出每个单词出现的次数”

   list2.removeAll(list1);

   for(String w : list2) {
          map.put(w, 0);
    }

    for(Entry<String, Integer> e : map.entrySet) {
          int n = Collections.frequency(list2, e.getKey());
          e.setValue(n);
    }

答案 1 :(得分:1)

要删除另一个集合中存在的所有元素,请使用removeAll。这是Collection接口中的可选操作,ArrayList和HashSet都实现了它。

words.removeAll(webWords);

要构建频率表,您必须使用Set,因为Sets只保留每个元素中的一个。您需要使用列表并创建Map<String, Integer>以将每个单词映射到它出现的次数。要构建它,你可以这样做:

for (String word : words) {
    if (freqMap.containsKey(word)) {
        freqMap.put(word, freqMap.get(word) + 1); // increment
    } else {
        freqMap.put(word, 1); // begin at 1 if it was not present
    }
}

答案 2 :(得分:0)

组合术语和计数的简单方法是使用HashMap,将单词作为键,将出现次数作为值。我不记得Java的确切符号,但我希望这样:

HashMap words = new HashMap();
while ( st.hasMoreTokens())
{
   s = st.nextToken();
   if ( words.containsKey(s) )
    {
        // probably not how indexing is done, but would be in most languages :p
        words[s]= words[s]+1;
     }
   else 
     {
       words.put( s, 1 );
     }
}

这样你最终会得到一个包含所有独特单词的HashMap以及每个单词的出现次数。