3

我正在创建一个歌曲播放应用程序。我有一组保存在 SharedPreferences 中。我想从中添加和删除文件名,并保持它们与我添加它们的顺序相同,例如:

recentsp = getSharedPreferences("recentkey", Context.MODE_PRIVATE);

    recent = recentsp.getStringSet("recent", recent);
    recentedited = recent;

    if (recentedited.contains(string) {
        recentedited.remove(string);
        Log.i(TAG, "Recent exists, removing song");
        SharedPreferences.Editor editor = recentsp.edit();
        editor.clear();
        editor.putStringSet("recent", recentedited);
        editor.commit();
    }

        recentedited.add(string);
    Log.i(TAG, "adding song to recent");
        SharedPreferences.Editor editor = recentsp.edit();
        editor.clear();
        editor.putStringSet("recent", recentedited);
        editor.commit();

但是当我在 ListView 中查看这些时,问题就出现了。我希望它们按照我添加它们的顺序进行,以便我可以拥有最近播放的部分,但有时它们根本不动,或者它们可能在一开始就结束了。似乎是随机的。我错过了什么吗?

编辑:

我通过在初始化步骤中执行此操作来检查以确保 SharedPreferences 不为空...

编辑:

即使使用 LinkedHashSet 我仍然没有得到正确的排序。我只在 SharedPreferences 为空时才调用它,所以我不确定如何确保我使用的是 LinkedHashSet。

        recentsp = getSharedPreferences("recentkey", Context.MODE_PRIVATE);
    recent = recentsp.getStringSet("recent", null);
    if (recent == null) {

        recent = new LinkedHashSet<String>();
        SharedPreferences.Editor editor = recentsp.edit();
        editor.clear();
        editor.putStringSet("recent", recent);
        editor.commit();
    }
4

3 回答 3

6

如果您正在寻找Set保留插入顺序的接口的实现,请从切换HashSet到:LinkedHashSet。所有标准Set行为都保持不变,增加了插入顺序迭代。

从相关的 JavaDoc:

Set 接口的哈希表和链表实现,具有可预测的迭代顺序。此实现与 HashSet 的不同之处在于它维护一个双向链表,该列表贯穿其所有条目。该链表定义了迭代顺序,即元素插入集合的顺序(插入顺序)。请注意,如果将元素重新插入集合中,则插入顺序不受影响。(如果 s.add(e) 被调用,而 s.contains(e) 将在调用之前立即返回 true,则元素 e 被重新插入到集合 s 中。)

此实现使其客户免于 HashSet 提供的未指定、通常混乱的排序,而不会增加与 TreeSet 相关的成本。它可用于生成与原始集合具有相同顺序的集合的副本,而不管原始集合的实现如何

于 2016-02-02T23:28:00.837 回答
2

我有一组保存在 SharedPreferences 中。我想从中添加和删除文件名,并保持它们的顺序相同

这是不可能的。您不控制Set实施,并且不需要Set订购 a。您的选择是:

  1. 不要担心订单,或者

  2. 不要使用带有 的字符串集SharedPreferences,而是将值存储在单个字符串中(例如,编码为 JSON),或者

  3. 不要使用SharedPreferences,而是使用其他一些数据存储选项(例如,SQLite 数据库、JSON 文件)

于 2016-02-03T00:00:52.767 回答
0

也许只使用 ArrayList 而不是 Set - 看起来您已经有代码来确保该项目已在集合中被删除和添加 - 该模式应该与 ArrayList 一起使用。

如果您需要代码将列表序列化为首选项,这个较旧的问题有一个示例Save ArrayList to SharedPreferences或使用 GSON 之类的东西来存储和检索在 SharedPreferences 中存储列表或集合

于 2016-02-02T23:59:40.880 回答