在游戏中,我试图保留用户列表并按分数排序,以便我可以在任何给定时间查询列表并按分数返回(例如)前十名用户。此列表应该是线程安全的。我设想使用userName字符串作为键,值将是一个实现Comparable的User对象,并具有displayName和score等属性。因此,User对象将具有compareTo方法,该方法将比较score属性以确定其位置。
我正在考虑使用ConcurrentSkipListMap,但正如我所知,Map(而不是Set)使用键进行排序。我希望列表按User对象的score属性排序,但仍然使用Map,因为我需要能够访问任何给定用户并从线程修改其score属性。
似乎没有使用我自己的Comparator来解决我的问题,因为我怀疑我可以访问相关的值进行比较。我可以使用ConcurrentSkipListSet但是访问列表来修改单个用户的分数将是(我想象)一个昂贵的操作(由于需要每次迭代)。
有人能建议如何做到这一点吗?
答案 0 :(得分:3)
不,我认为你不能。用于排序的比较器与用于索引的比较器相同。您可能需要维护2个集合。一个用于保持用户分数的顺序,用于按名称引用用户。
答案 1 :(得分:1)
get(key)
取决于比较器(能够找到密钥)。您建议一个依赖于get(key)
的比较器(根据该比较来访问密钥的映射值)。这必然会导致无限递归和堆栈溢出(好的一面是,你在正确的网站发帖!!)
答案 2 :(得分:1)
我认为你有3个选择:
我不会假设1和1之间哪个更快。我会用你的预期用法和量度来尝试它们,看看最糟糕的是什么。
如果您真的只对前n个分数感兴趣,那么可以单独维护该列表。所以有你的用户名地图为每个人打分,但也保留一小部分最高分(及其用户)。每次添加/更新某人的分数时,只需检查最高分数列表中的分数,如果它比那里的最小分数大,那么只需添加它并使其低一些。这与上面的建议3类似,但开销较小,可能更容易维护。