进程间通信学习系列(二)——简单了解Binder机制

最近得空,打算学习研究一下进程间通信,主要参考任玉刚大神的《Android开发艺术探索》一书,并查阅相关博客。将自己的学习总结记录下来,方便自己,帮助他人。如有错误,还请指正。

一、什么是IPC机制

IPC : Inner-Process Communication,进程间的通信。IPC机制不是Android独有的,任何一个操作系统都有其对应的IPC机制。虽然Android是基于Linux内核的操作系统,但是Android有其自己的进程间通信方式。

二、Android常见的实现进程间通信的方式

这里只是罗列出实现方式,具体实现方式及其优缺点会在后续文章中写出。
1.使用Bundle传递数据
2.使用文件共享
3.使用AIDL
4.使用ContentProvider(底层实现是AIDL)
5.使用Messenger(底层实现是AIDL)
6使用Socket

三、多进程

既然是进程间通信,那至少的有两个进程。进程间通信包括两种情景:1.两个应用(两个应用当然至少包括连个进程)之间进行数据交换;2.一个应用中包含多个进程,这种情况就要了解Android的多进程机制了。

Android实现多进程很简单,并且只有一种方式:给四大组件在Manifest.xml文件中指定android:proccess属性。如下:创建3个Activity,并为它们指定process属性。

  <!--未指定process属性,运行在默认进程,默认进程名为包名-->
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

        <!--指定进程为:remote,“:”是一种简写,要在进程名前附加当前包名,所以全进程名为:com.anyan.ipcdemo:remote-->
        <activity
            android:name=".SecondActivity"
            android:process=":remote" />
        <!--指定进程为com.anyan.ipcdemo.remote,全写,不会再附加包名-->
        <activity
            android:name=".ThirdActivity"
            android:process="com.anyan.ipcdemo.remote" />


分别启动三个activity,通过DDMS窗口查看,可以看到三个Activity分别运行在process属性指定的进程中:






注:以“:”开头的进程属于当前应用的私有进程;全写方式的进程属于全局进程。

Android多进程虽然使用方式简单,直接指定process属性即可,但是使用多进程模式会引入各种问题,一定要多加注意。例如:

创建一个类,里面有一个static修饰的int值,如下:

public class Constant {
    public static int CODE = 0;
}
在MainActivity中修改CODE的值,并在改变前后打印其值:

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        Log.e(TAG, "=====MainActivity onCreate:修改前:"+Constant.CODE );
        Constant.CODE = 2;
        Log.e(TAG, "=====MainActivity onCreate:修改后:"+Constant.CODE );
    }

启动SecondActivity,查看打印CODE的值:

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_second);
        Log.e(TAG, "=====SecondActivity onCreate:"+Constant.CODE );
    }


打印结果如下:




可以看到在MainActivity修改了CODE的值后,在SecondActivity中CODE值并没有变化,Why?因为这是两个进程!Android会为每一个进程分配一个独立的虚拟机,不同的虚拟机在内存分配上有不同的地址空间,导致不同进程访问同一个内存对象会产生多个副本,且互不干扰,所以当一个进程修改了某个内存对象的属性值,另一个进程的该内存对象却不会改变。

总结来说,多进程会有以下问题:

1.静态成员和单例模式完全失效;

2.线程同步机制完全失效;

3.SharePreferences可靠性下降,存在并发读写问题;

4.Application会多次创建。

四、序列化

以上提到多进程带来的问题,为了解决这些问题,Android提供了多种进程间通信方式来尽量解决或者避免这些问题。进程间通信需要交换数据,除了基本数据类型的数据外,我们常常需要传递我们自己的Bean类,这就需要序列化。序列化有两种方式:
1.Serializable接口
Java提供的空接口,直接implements即可,指定serialVersionUID(影响反序列化的过程);
自动生成serialVersionUID可参考博客:
2.Parcelable接口

Android推荐的序列化方式,使用稍微麻烦,但是效率高,主要用在内存序列化上。优先使用此种方式。

Android Studio可以使用插件(自动化快速实现Parcelable接口序列化)一键生成Parcelable序列化.

 

进程间通信学习系列(二)——简单了解Binder机制


猜你喜欢

转载自blog.csdn.net/anyanyan07/article/details/79076608