2 myc 100 myc_100 于 2013.04.28 17:16 提问

在 Activity 之间如何传递 LinkedHashMap?

我想在activities 之间传递 LinkedHashMap,代码如下:
Activity A

LinkedHashMap mLinkedHashMap = new LinkedHashMap<String, Object>();
// setting data in map
Bundle bundle = new Bundle();
bundle.putSerializable("OBJECTS_LINKED_HASHMAP", mLinkedHashMap);  
Intent intent = new Intent(this, ActivityB.class); 
intent.putExtras(bundle);
startActivity(intent);

在 Activity 中当接受包对象时,却获取"Class cast exception" 错误信息
Activity B

Bundle bundle = this.getIntent().getExtras();
LinkedHashMap mLinkedHashMap = new LinkedHashMap<String, Object>();
mLinkedHashMap = (LinkedHashMap<String, Object>) bundle.getSerializable("OBJECTS_LINKED_HASHMAP");

获得异常:

ClassCastException: java.util.HashMap cannot be cast to LinkedHashMap

我查相关资料得知 LinkedHashMap 也实现 Serializable 接口。
我使用 LinkedHashMap 保持对象的顺序。
在 Activity 之间如何传递 LinkedHashMap?

4个回答

feifei454498130
feifei454498130   2013.04.29 22:17
已采纳

关于在Activity之间传对像,最好的方法就是共享内存。

设计一个类作为单例模式,如下

public class Share {

private static Share current;

public static Share getInstance() {
    synchronized (Share.class) {
        if(current == null) {
            current = new Share();
        }
        return current;
    }
}

final HashMap<String, Object> memoryMap;
public Share() {
    memoryMap = new HashMap<String, Object>();
}

public void put(String key, Object value) {
    memoryMap.put(key, value);
}

public Object get(String key) {
    return memoryMap.get(key);
}

}

然后在Activity1里传一个key字符串值到Activity2里,再在Activity2里去获取Share里的对象,这样子既不用序列化也减少序列化所使用时间,总之,方便,快捷
huzgd
huzgd   2013.04.29 16:32

如果是同一个进程中且即传即用,可考虑直接用全局变量静态变量,即直接在ActivityB定义public static LinkedHashMap mLinkedHashMap,然后在ActivityA中直接写ActivityB. mLinkedHashMap= xxx赋值,在ActivityB启动时直接读取mLinkedHashMap。由于传过去之后马上就使用,因此不用担心内存不足被释放之类的问题。
如果是不同进程,就只能做系列化反系列化了。

franzhong
franzhong   2013.04.28 19:46

只能转化到HashMap,转化会失败
我传个字符串转为HashMap成功了,一步到位好像有难度,你再加油摸索一下
(你若传对象,那个class像似要继承Serializable接口)
//mainActivity2

if (getIntent().getSerializableExtra("OBJECTS_LINKED_HASHMAP") != null){        
            Bundle bundle2 = this.getIntent().getExtras();
            HashMap<String, Object>   user_info = (HashMap<String, Object>) bundle2.getSerializable("OBJECTS_LINKED_HASHMAP");
            String str = user_info.toString();
            System.out.println("Got str:"+str); // Got str:{TEST=this is a test}
        }

//mainActivity1

LinkedHashMap mLinkedHashMap = new LinkedHashMap<String, Object>();
            mLinkedHashMap.put("TEST", "this is a test");
            Bundle bundle = new Bundle();
            bundle.putSerializable("OBJECTS_LINKED_HASHMAP", mLinkedHashMap); 
            Intent intent = new Intent(this, UserActivity.class); 
            intent.putExtras(bundle);
            startActivity(intent);
wqy19920429
wqy19920429   2015.12.22 10:03

The Extras in an intent are key-value-pairs in a Bundle, which is actually a HashMap.

Java Code:
1
intent.putExtra("tests.test.MyApp.A.EXTRA_KEY", populateSelectedEntryList(selectedResultEntry));
In the above snippet, we are adding the key-value-pair of "tests.test.MyApp.A.EXTRA_KEY" (as the key) and the LinkedHashMap returned by populateSelectedEntryList(selectedResultEntry) (as the value) to that internal HashMap.

Now when we call startActivity with the intent containing that Extras Bundle, the Android system needs to convert that Bundle into Byte stream, i.e. serialize the Bundle (because (1) the Activity to be started might be started in another process, so the system serializes and then deserializes the objects in the Bundle, so that it can recreate them in the other process. (2) Android saves the contents of the intent in some system tables, so that it can recreate the intent later if needed).

So in the process of doing so, the system has to see what type the "values" in the extras' key-value-pairs are (in order to do the serialization in the most efficient way), by comparing them against a pool of known Object's ( like Integer, Long, String, Map, List, Bundle etc.), one of which is a Map. So the system finds out that the type of value is Map, so it serializes it and marks it as having the type Map.

When this value is deserialized in

Java Code:
1
LinkedHashMap dataHashMap = (LinkedHashMap) intent.getSerializableExtra("tests.test.MyApp.A.EXTRA_KEY");
Android converts that Map into a HashMap, and there is No way to change this behavior of Android. :-|
无法在Activity之间直接传递LinkHashMap看来是Android反序列化bundle的一个“bug”了,看来只能使用其他方式传递了,比如json

Csdn user default icon
上传中...
上传图片
插入图片
准确详细的回答,更有利于被提问者采纳,从而获得C币。复制、灌水、广告等回答会被删除,是时候展现真正的技术了!