您的当前位置:首页正文

Bundle的使用与解析

2024-11-29 来源:个人技术集锦

Bundle

应用场景举例

Activity:onCreat()、onSaveInstanceState()
Fragment: setArguments()
Message:setData()

源码

//位于android.os包中,final类
public final class Bundle extends BaseBundle implements Cloneable, Parcelable
//实现了Cloneable, Parcelable接口,因此需要重写的方法
public Object clone()
public int describeContents()
public void writeToParcel(Parcel parcel, int flags)
public void readFromParcel(Parcel parcel)
public static final Parcelable.Creator<Bundle> CREATOR = new Parcelable.Creator<Bundle>()

构造方法

Bundle()
Bundle(ClassLoader loader)
Bundle(int capacity)
Bundle(Bundle b)
Bundle(PersistableBundle b)

获取只包含一个键值对的Bundle对象

public static Bundle forPair(String key, String value) {
    Bundle b = new Bundle(1);
    b.putString(key, value);
    return b;
}

put与get方法

​ put()与get()中的key值均为String类型,put()的value值类型为传入的数据类型

相关保存方法相关读取方法
putBoolean()getBoolean()
putByte()getByte()
putChar()getChar()
putShort()getShort()
putFloat()getFloat()
putCharSequence()getCharSequence()
putParcelable()getParcelable()
putSize()getSize()
putSizeF()getSizeF()
putParcelableArray()getParcelableArray()
putParcelableArrayList()getParcelableArrayList()
putSparseParcelableArray()getSparseParcelableArray()
putIntegerArrayList()getIntegerArrayList()
putStringArrayList()getStringArrayList()
putCharSequenceArrayList()getCharSequenceArrayList()
putSerializable()getSerializable()
putBooleanArray()getBooleanArray()
putByteArray()getByteArray()
putShortArray()getShortArray()
putCharArray()getCharArray()
putFloatArray()getFloatArray()
putCharSequenceArray()getCharSequenceArray()
putBundle()getBundle()
putBinder()getBinder()

清除Bundle数据

清除Bundle中所有数据:clear()

Bundle存取数据具体实现

​ 内部维护了一个ArrayMap,具体定义是在其父类BaseBundle中

void putBoolean(String key, boolean value) {
    unparcel();
    //mMap即为ArrayMap
    mMap.put(key, value);
}
boolean getBoolean(String key) {
    unparcel();
    if (DEBUG) Log.d(TAG, "Getting boolean in "+ Integer.toHexString(System.identityHashCode(this)));
    return getBoolean(key, false);
}
//getBoolean()
boolean getBoolean(String key, boolean defaultValue) {
    unparcel();
    //通过key从ArrayMap里读出保存的数据
    Object o = mMap.get(key);
    if (o == null) {
        return defaultValue;
    }
    try {
        //转换成对应的类型返回
        return (Boolean) o;
    } catch (ClassCastException e) {
        typeWarning(key, o, "Boolean", defaultValue, e);
        //转换异常时返回缺省值
        return defaultValue;
    }
}

ParcelledData解析

​ 三种取值情况:
mParcelledData = EMPTY_PARCEL
mParcelledData = Parcel.obtain()
mParcelledData = null

//定义,mParcelledData = null
Parcel mParcelledData = null;
//创建Bundle
BaseBundle(BaseBundle b) {
    if (b.mParcelledData != null) {
        if (b.mParcelledData == EMPTY_PARCEL) {
            //EMPTY_PARCEL
            mParcelledData = EMPTY_PARCEL;
        } else {
            //Parcel.obtain()
            mParcelledData = Parcel.obtain();
            mParcelledData.appendFrom(b.mParcelledData, 0, b.mParcelledData.dataSize());
            mParcelledData.setDataPosition(0);
        }
    } else {
        mParcelledData = null;
    }

    if (b.mMap != null) {
        mMap = new ArrayMap<String, Object>(b.mMap);
    } else {
        mMap = null;
    }

    mClassLoader = b.mClassLoader;
}

unparcel()方法解析


/* package */ synchronized void unparcel() {
    if (mParcelledData == null) {
        //如果mParcelledData为null,直接返回
        if (DEBUG) Log.d(TAG, "unparcel " + Integer.toHexString(System.identityHashCode(this))
                + ": no parcelled data");
        return;
    }
	//如果mParcelledData为EMPTY_PARCEL,创建一个容量为1的ArrayMap对象
    if (mParcelledData == EMPTY_PARCEL) {
        if (DEBUG) Log.d(TAG, "unparcel " + Integer.toHexString(System.identityHashCode(this))
                + ": empty");
        if (mMap == null) {
            mMap = new ArrayMap<String, Object>(1);
        } else {
            mMap.erase();
        }
        //mParcelledData置为null
        mParcelledData = null;
        return;
    }
	//如果mParcelledData为Parcel.obtain(),创建一个ArrayMap,再将数据存储到ArrayMap中
    int N = mParcelledData.readInt();
    if (DEBUG) Log.d(TAG, "unparcel " + Integer.toHexString(System.identityHashCode(this))
            + ": reading " + N + " maps");
    if (N < 0) {
        return;
    }
    if (mMap == null) {
        mMap = new ArrayMap<String, Object>(N);
    } else {
        mMap.erase();
        mMap.ensureCapacity(N);
    }
    mParcelledData.readArrayMapInternal(mMap, N, mClassLoader);
    //mParcelledData回收并置为null
    mParcelledData.recycle();
    mParcelledData = null;
    if (DEBUG) Log.d(TAG, "unparcel " + Integer.toHexString(System.identityHashCode(this)) + " final map: " + mMap);
}
显示全文