一、什么是多进程
如果android系统相当于一个大的工厂,那进程就是工厂中的一个车间,线程是车间中的流水线。
二、为什么要使用多进程
使用多进程的好处是可以扩展程序的内存空间(因为一个进程占用系统内存空间是有限的),增加程序的流畅性,但也可能造成程序过于臃肿,而且进程之间是完全隔离的,可有效杜绝一些安全问题。
三、如何使用?
<service android:name=".MessengerService"
android:process="com.messenger.service"
android:enabled="true"
android:exported="true"
/>
一般通过android:process关键字在manifests文件中定义,程序默认的进程是包名,如果使用:+ xxxx的形式来定义新进程,则会形成包名+: + xxxxx的新进程。
四、进程间的通信
1、使用Messenger传递信息
对于单线程的多进程之间通信,可使用messenger来通信,因为他不会锁定线程,所以是非安全的,但如果是单线程多进程就无所谓了。
下面是一个服务类的代码。
public class MessengerService extends Service {
private Messenger messenger;
private Handler handler = new Handler(){
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
Log.i("info","MessengerService");
Message replayMsg = Message.obtain();
try {
msg.replyTo.send(replayMsg);
} catch (RemoteException e) {
e.printStackTrace();
}
}
};
@Override
public void onCreate() {
super.onCreate();
messenger = new Messenger(handler);
}
@Nullable
@Override
public IBinder onBind(Intent intent) {
return messenger.getBinder();
}
}
首先自定义一个类,记得在manifests中注册为新的进程,新建一个Messenger类给他传入handler,然后在onBind方法中传入messenger.getBinder()。
然后是主进程代码:
public class MainActivity extends AppCompatActivity {
private Messenger messenger;
private Button button;
private Handler handler = new Handler(){
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
Log.i("info","MainActivity-handler");
}
};
private Messenger replayMessenger = new Messenger(handler);
private ServiceConnection serviceConnection = new ServiceConnection() {
@Override
public void onServiceConnected(ComponentName componentName, IBinder iBinder) {
messenger = new Messenger(iBinder);
}
@Override
public void onServiceDisconnected(ComponentName componentName) {
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
button = (Button) findViewById(R.id.main_button);
bindService(new Intent(this,MessengerService.class),serviceConnection, Context.BIND_AUTO_CREATE);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
if(messenger!=null){
Message msg = Message.obtain(handler,0);
msg.replyTo = replayMessenger;
try {
messenger.send(msg);
Log.i("info","MainActivity");
} catch (RemoteException e) {
e.printStackTrace();
}
}
}
});
}
}
跟服务中的方法类似,可以通过绑定服务得到service传过来的Messenger,再通过Messenger的send方法传递数据。还可以携带用一个新的Messenger传入自己的handler用来让service给main方法回传数据。
PS:bindService()方法完成绑定需要一段时间,此时是无法获得Messenger的,其次是send方法无法直接传递包括String在内的没有序列化的数据,如果要传递可使用Bundle类。
2、使用ALDI传递信息
没怎么用过。。有使用经验后再来补。。