Android - 通过意图传递哈希图

问题描述 投票:0回答:3

我试图通过一个意图传递一个自定义对象的Hashmap。

我试图使用parcelable,因为我读到的是android中正确的方法(即parcelable高于serializable)。

然而,当我尝试使用getParcelable获取hashmap时,它无法在意图中找到我的hashmap,但getSerializable可以。

使用serializable来做hashmaps可以吗?这是我唯一的选择吗?

java android hashmap parcelable serializable
3个回答
3
投票

你当然可以序列化你的地图,只要你的Objects是可序列化的。你也可以创建一个单独的单人类(DataStore之类的)来保存你的数据。这样你就不需要将数据从Activity传递到Activity。或者,更简单的,把数据保存在一个公共静态变量中。


0
投票

java.util.HashMap 不是 包裹式,所以你的选择是

  • 使用putgetSerializable, 这在你的应用程序中会很好地工作。
  • 将HashMap编码为json或其他可遥控的格式(如果在您的应用程序之外发送)。
  • 将地图条目逐一取出并直接放入Bundle中(假设它们有字符串键)。

0
投票

你必须添加一个 "包装"。它很丑陋,但工作...

/**
 * Provides a way to wrap a serializable {@link Map} in order to preserve its class
 * during serialization inside an {@link Intent}, otherwise it would be "flattened"
 * in a {@link android.os.Parcel} and unparceled as a {@link java.util.HashMap}.
 */
public class MapWrapper<T extends Map & Serializable> implements Serializable {

    private final T map;

    public MapWrapper(@NonNull T map) {
        this.map = map;
    }

    public T getMap() {
        return map;
    }

    /**
     * Add extra map data to the intent. The name must include a package prefix, for example
     * the app com.android.contacts would use names like "com.android.contacts.ShowAll".
     * <p>
     * The provided map will be wrapped to preserve its class during serialization.
     * Use {@link #getMapExtra(Intent, String)} to deserialize it.
     *
     * @param intent The intent to add data to.
     * @param name   The name of the extra data, with package prefix.
     * @param map    The map data value.
     *
     * @return The same {@link Intent} object, for chaining multiple calls into a single statement.
     *
     * @see Intent#putExtra(String, Serializable)
     */
    @NonNull
    public static <T extends Map & Serializable> Intent putMapExtra(
            @NonNull Intent intent, @NonNull String name, @NonNull T map) {
        return intent.putExtra(name, new MapWrapper<>(map));
    }

    /**
     * Retrieve extra map data from the intent.
     *
     * @param intent The intent to retrieve data from.
     * @param name   The name of the desired extra item.
     *
     * @return The value of an extra map item that was previously added with
     * {@link #putMapExtra(Intent, String, Map)} or {@code null} if no data was found.
     *
     * @throws ClassCastException
     * If the {@link Serializable} object with the specified name is not of type
     * {@link MapWrapper} or if the wrapped {@code Map} is not of type {@link T}.
     * 
     * @see Intent#getSerializableExtra(String)
     */
    @Nullable
    public static <T extends Map & Serializable> T getMapExtra(
            @NonNull Intent intent, @NonNull String name)
            throws ClassCastException {
        final Serializable s = intent.getSerializableExtra(name);
        //noinspection unchecked
        return s == null ? null : ((MapWrapper<T>)s).getMap();
    }

}

更多信息 https:/medium.comthe-wtfilesthe-mysterious-case-the-bundle-and-the-map-7b15279a794e

© www.soinside.com 2019 - 2024. All rights reserved.