假设我有一个文件,例如具有以下类型的数据:
info1 word1
info2 word2
info3 word3
info2 word4
等
现在,我想为每行中的单词创建一个映射函数。所以我最初阅读该行,使用空格拆分它,然后得到这个词。
现在这个词就是价值。我知道所有的话都是不同的和独特的。但是,这些信息可能并不是唯一的。
关于密钥,因为我最感兴趣的是与每个单词相关的信息,我只是为它创建一个基本上就是所有行的字符串。
我知道这些信息可能没有什么不同,但肯定是这些,因为这些词语肯定是不同的。
该文件有40000行,但HashMap的大小为38490。
我不明白这里发生了什么。我的逻辑错了吗?
这是代码:
private static void loadInfo(HashMap<String, String> info, File File){
try {
BufferedReader br = new BufferedReader(new FileReader(file));
String[] dataInLine = new String[2];
String line = br.readLine();
int counter = 0;
while (line != null) {
lineData = line.split("\\s+");
info.put(lineData[1], line);
line = br.readLine();
counter++;
}
System.out.println(counter); //counter shows the correct amount of lines
System.out.println(info.size()); //this shows less than the amount of lines
} catch (IOException io) {
}
}
提前致谢
答案 0 :(得分:3)
如果你有重复的密钥会发生这种情况; put
将覆盖之前的值。
答案 1 :(得分:2)
很可能你的单词列表实际上并不是唯一的。您可以在致电.put()
之前进行检查,以确定某个字词是否已存在并报告重复:
while (line != null) {
lineData = line.split("\\s+");
final String word = lineData[1];
final String previous = info.get(word);
if (previous != null) {
System.err.println("Duplicate at count "+line+" of word "+word);
System.err.println(" original line: "+previous);
System.err.println(" new line: "+line);
}
info.put(word, line);
line = br.readLine();
counter++;
}
答案 2 :(得分:0)
你可能做有一些重复的密钥。
检查是否要替换以前的值的简单方法是查看put
的返回值:
String last = info.put(lineData[1], line);
if( last != null )
System.err.println("Warning: replaced value for key "+lineData[1]+", last value was: "+last);
答案 3 :(得分:0)
你可能有重复的密钥,例如示例中的“info2”映射到“word2”和“word4”。
如果您需要具有映射到多个值的键,则需要“多图”。您可以使用类型HashMap<String, Set<String>>
创建自己的(每个键映射到一组值)。或者使用预先存在的一个,例如Apache Commons中的那个。
使用您自己的,每次要添加映射时,您需要检查密钥是否存在;如果没有将它映射到空集。然后添加映射,将值放入该键的集合中。
HashMap<String, Set<String>> info;
...
if (!info.contains(lineData[1])) {
info.put(lineData[1], new HashSet<String>());
}
info.get(lineData[1]).put(line);