简体   繁体   English

Android - 通过意图传递哈希图

[英]Android - passing hashmap through intent

I'm trying to pass a Hashmap of custom objects through an intent.我正在尝试通过意图传递自定义对象的 Hashmap。

I am trying to use parcelable as that's what i read is the correct way to do things in android (ie parcelable over serializable).我正在尝试使用parcelable,因为这就是我读到的在android中做事的正确方法(即parcelable over serializable)。

However, when i try and get the hashmap using getParcelable, it can't find my hashmap in the intent, but getSerializable can.但是,当我尝试使用 getParcelable 获取哈希图时,它无法在意图中找到我的哈希图,但 getSerializable 可以。

Is it OK to use serializable for hashmaps?可以对哈希图使用可序列化吗? Is this my only option?这是我唯一的选择吗?

You can of course serialize your map, as long as your Objects are serializable.您当然可以序列化您的地图,只要您的对象是可序列化的。 What you also could do is creating a separate singleton class (DataStore or so?) that saved your data.您还可以做的是创建一个单独的单例类(DataStore 左右?)来保存您的数据。 This way you don't need to pass the data from Activity to Activity.这样您就不需要将数据从 Activity 传递到 Activity。 Or, even simpler, save the data in a public static variable.或者,更简单的是,将数据保存在公共静态变量中。

java.util.HashMap is not Parcelable , so your options are: java.util.HashMap不是Parcelable ,所以你的选择是:

  • use put/getSerializable, which will work fine within your app使用 put/getSerializable,它可以在您的应用程序中正常工作
  • encode the HashMap as json or another remotable format if sending outside your app如果在您的应用程序之外发送,请将 HashMap 编码为 json 或其他远程格式
  • take out the map entries one by one and put them in the Bundle directly (assuming they have string keys)将map条目一一取出,直接放入Bundle中(假设有字符串key)

You have to add a "wrapper".您必须添加一个“包装器”。 It is ugly but working...这是丑陋的,但工作...

/**
 * 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();
    }

}

More informations on https://medium.com/the-wtf-files/the-mysterious-case-of-the-bundle-and-the-map-7b15279a794e有关https://medium.com/the-wtf-files/the-mysterious-case-of-the-bundle-and-the-map-7b15279a794e 的更多信息

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM