如何使用包含 Hashmap 和 SparseArray 的自定义类实现 parcelable?

Posted

技术标签:

【中文标题】如何使用包含 Hashmap 和 SparseArray 的自定义类实现 parcelable?【英文标题】:How to implement parcelable with my custom class containing Hashmap and SparseArray? 【发布时间】:2019-02-20 11:52:35 【问题描述】:

我需要在我的自定义类“ArtistInfo”中实现 parcelable 结构如下:

公共类 ArtistInfo 实现 Parcelable 私人弦乐艺术家; //专辑名称到歌曲ID列表 私有HashMap>专辑信息; // 歌曲 ID 到歌曲信息 私有 SparseArray 歌曲地图; 受保护的艺术家信息(包裹) 艺术家 = in.readString(); public static final Creator CREATOR = new Creator() @覆盖 public ArtistInfo createFromParcel(包裹在) 返回新的 ArtistInfo(in); @覆盖 公共 ArtistInfo[] newArray(int size) 返回新的 ArtistInfo[大小]; ; 公共字符串 getArtist() 回归艺术家; 公共无效setArtist(字符串艺术家) this.artist = 艺术家; public void addSongsInfoToAlbum(列出歌曲信息,字符串专辑) if (albumInfo == null) 专辑信息 = 新的 HashMap(); if (songsMap == null) songMap = new SparseArray(); ListsongIds = new ArrayList(); 对于(歌曲信息歌曲信息:歌曲信息) songIds.add(songInfo.getId()); songMap.put(songInfo.getId(), songInfo); ListsongIdsForAlbum = getSongIdsForAlbum(album); songIdsForAlbum.addAll(songsIds); 专辑信息.put(专辑,songsIdsForAlbum); 私人列表 getSongIdsForAlbum(字符串专辑) if (albumInfo == null) 返回新的 ArrayList(); ListsongIds = albumInfo.get(album); 返回 songIds == null ?新的 ArrayList() : songIds; 公共HashMap> getAlbumInfo() 返回专辑信息; 公共稀疏数组 getSongsMap() if (songsMap == null) songMap = new SparseArray(); 返回歌曲地图; @覆盖 公共字符串 toString() 返回 "艺术家信息" + "艺术家='" + 艺术家 + '\'' + ", albumInfo=" + albumInfo.toString() + ", songMap=" + songMap.toString() + ''; @覆盖 公共 int describeContents() 返回0; @覆盖 公共无效writeToParcel(包裹目的地,int标志) dest.writeString(艺术家);

以下是上述类中使用的“SongInfo”类的结构:

公共类 SongInfo 实现 Parcelable 私人整数 id; 私有字符串名称; 私人字符串网址; public SongInfo(整数 id,字符串名称,字符串 url) 这个.id = id; this.name = 名称; 这个.url = url; 受保护的歌曲信息(包裹在) if (in.readByte() == 0) 身份证=空; 别的 id = in.readInt(); 名称 = in.readString(); url = in.readString(); public static final Creator CREATOR = new Creator() @覆盖 public SongInfo createFromParcel(Parcel in) 返回新的 SongInfo(in); @覆盖 公共 SongInfo[] newArray(int size) 返回新的 SongInfo[大小]; ; 公共整数 getId() 返回标识; 公共无效 setId(整数 id) 这个.id = id; 公共字符串 getName() 返回名称; 公共无效集合名称(字符串名称) this.name = 名称; 公共字符串 getUrl() 返回网址; 公共无效setUrl(字符串网址) 这个.url = url; @覆盖 公共 int describeContents() 返回0; @覆盖 公共无效writeToParcel(包裹目的地,int标志) 如果(id == null) dest.writeByte((字节) 0); 别的 dest.writeByte((字节) 1); dest.writeInt(id); dest.writeString(name); dest.writeString(url);

现在你可以看到在 SongInfo 类中实现 Parcelable 接口没有问题,但是我无法理解如何读写 albumInfosongsMap Constructor 和 writeToParcel 方法中的变量。有人可以帮我理解我应该如何继续。谢谢!

【问题讨论】:

【参考方案1】:

这个想法是遍历albumInfosongsMap中的每个项目,然后将其添加到Parcelable中。

写信给包裹。

@Override
public void writeToParcel(Parcel dest, int flags) 
    dest.writeString(artist);

    // Write album info
    dest.writeInt(albumInfo.size());
    for (Map.Entry<String, List<Integer>> item : albumInfo.entrySet()) 
        dest.writeString(item.getKey());
        dest.writeList(item.getValue());
    

    // Write song map
    dest.writeInt(songsMap.size());
    for (int i = 0; i < songsMap.size(); i++) 
        int key = songsMap.keyAt(i);
        dest.writeInt(key);
        dest.writeParcelable(songsMap.get(key), flags);
    

从包裹中读取

protected ArtistInfo(Parcel in) 
    artist = in.readString();

    // Read album info
    albumInfo = new HashMap<>();
    int albumInfoSize = in.readInt();
    for (int i = 0; i < albumInfoSize; i++) 
        String key = in.readString();
        List<Integer> value = new ArrayList<>();
        in.readList(value, null);
        albumInfo.put(key, value);
    

    // Read song map
    songsMap = new SparseArray<>();
    int songsMapSize = in.readInt();
    for (int i = 0; i < songsMapSize; i++) 
        int key = in.readInt();
        SongInfo value = in.readParcelable(SongInfo.class.getClassLoader());
        songsMap.put(key, value);
    

【讨论】:

那行得通。谢谢!您能否解释一下函数 writeToParcel 中标志的含义,因为我不明白它是如何工作的。 @tom 实际上我并不关心这个标志,所以我只是将传递给writeToParcel 方法的标志传递给。您可以查看此链接以找到您的答案***.com/questions/44203223/…

以上是关于如何使用包含 Hashmap 和 SparseArray 的自定义类实现 parcelable?的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 HashMap 并在 ArrayAdapter 中使用它来显示微调器中的值

Kotlin HashMap包含使用数组的键

在 JPA 中使用相同的实体键映射多个 HashMap

如何在迭代时从 HashMap 中删除键? [复制]

HashMap包含某个键,但告诉我它没有

HashMap到HashMap 使用流