1 android进程通信方式
方式 | 优点 | 缺点 | 适用场景 |
---|---|---|---|
AIDL | 有着强大的功能,支持一对多并发通信,支持实时通信 | 使用稍复杂,需要处理好线程同步 | 不同进程通过IPC方式访问服务,并且希望在服务中进行多线程处理 |
Binder | 简单,易用 | 单进程内使用,不能处理多线程 | 想利用IPC访问服务,但不需要处理多线程 |
sharedPrefences | 简单,易用 | 不可靠,也不支持并发 | 多进程简单键值对传递 |
Messenger | 可以利用IPC访问服务 | 不能处理多线程 | 想利用IPC访问服务,但不需要处理多线程 |
socket | 功能强大,可以通过网络共享传输字节流,支持一对多并发实时通信 | 实现细节稍微有点繁琐,不直接的RPC | 网络数据交换 |
Bundle | 简单易用 | 只能传输Bundle支持的数据类型 | 四大组件间的进程间通信 |
文件共享 | 简单易用 | 不适合搞并发场景,并且无法做到进程间的即时通信 | 无并发访问情形,交换简单的数据实时性不高的场景 |
ContentProvider | 在数据源访问方面功能强大,支持一对多并发数据共享,可通过Call方法扩展其他操作 | 可以理解为受约束的AIDL,主要提供数据源的CRUD操作 | 一对多的进程间的数据共享 |
广播(BroadcastReceiver):只要注册了广播,都能收到,有点范围广,缺点速度慢必须在一定时间完成处理操作,同其他Android四大组件一样,都不能执行耗时操作;
ContentProvider:暴露app的数据访问接口,让其他应该访问app数据.同时也能通过ContentProvider来访问第三方的一些app数据(如通讯录,日历等暴露接口的应用);
Intent:Intent是最高层级的封装,实质是封装了对Binder的使用,当然Intent也常常在同一进程中调用,只是把两种方式封装在一起。
2 AIDL数据类型
- Java 编程语言中的所有原语类型(如 int、long、char、boolean 等)
- String
- CharSequence
- List
- List 中的所有元素必须是以上列表中支持的数据类型,或者您所声明的由 AIDL 生成的其他接口或 Parcelable 类型,
- 支持 List 用作“泛型”类
- 生成的方法使用List接口,但另一方实际接收的具体类始终是ArrayList
- Map
- Map 中的所有元素必须是以上列表中支持的数据类型,或者您所声明的由 AIDL 生成的其他接口或 Parcelable 类型。
- 不支持泛型 Map
- 生成的方法使用Map接口,但另一方实际接收的具体类始终是HashMap
3 用法
// IDemoAIDL.aidl
package com.example.administrator.aidl_server.service;
// Declare any non-default types here with import statements
interface IDemoAIDL {
//计算num1 + num2
int add(int num1,int num2);
}
//编译后生成
public interface IDemoAIDL extends android.os.IInterface {
/**
* Local-side IPC implementation stub class.
*/
public static abstract class Stub extends android.os.Binder implements com.example.administrator.aidl_server.service.IDemoAIDL {
...
private static class Proxy implements com.example.administrator.aidl_server.service.IDemoAIDL {
private android.os.IBinder mRemote;
Proxy(android.os.IBinder remote) {
mRemote = remote;
}
@Override
public android.os.IBinder asBinder() {
return mRemote;
}
public java.lang.String getInterfaceDescriptor() {
return DESCRIPTOR;
}
@Override
public int add(int num1, int num2) throws android.os.RemoteException {
...
}
...
}
...
}
}
服务端:
public class IRemoteService extends Service {
public static final String TAG = "IRemoteService";
//客户端绑定service时会执行
@Override
public IBinder onBind(Intent intent) {
return iBinder;
}
private IBinder iBinder = new IDemoAIDL.Stub() {
@Override
public int add(int num1, int num2) throws RemoteException {
Log.e(TAG,"收到了来自客户端的请求" + num1 + "+" + num2 );
return num1 + num2;
}
};
}
AndroidManifest.xml
<application
...
<service android:name=".IRemoteService"
android:process=":remote"
android:exported="true">
<intent-filter>
<action android:name="com.example.administrator.aidl_server"/>
</intent-filter>
</service>
...
</application>
客户端:
com.example.administrator.aidl_client.MainActivity
public class MainActivity extends AppCompatActivity {
public static final String TAG = "MainActivity";
private EditText et_send_input,nub_1,nub_2;
private TextView tv_send;
private TextView tv_bind;
private IDemoAIDL iIDemoAIDLService;
private ServiceConnection conn = new ServiceConnection() {
//绑定服务,回调onBind()方法
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
iIDemoAIDLService = IDemoAIDL.Stub.asInterface(service);
}
@Override
public void onServiceDisconnected(ComponentName name) {
iIDemoAIDLService = null;
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
bindService();
et_send_input = findViewById(R.id.et_send_input);
nub_1 = findViewById(R.id.nub_1);
nub_2 = findViewById(R.id.nub_2);
tv_send = findViewById(R.id.tv_send);
tv_bind = findViewById(R.id.tv_bind);
tv_send.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
try {
int nub1 = Integer.parseInt(nub_1.getText().toString().trim());
int nub2 = Integer.parseInt(nub_2.getText().toString().trim());
int result = iIDemoAIDLService.add(nub1,nub2);
et_send_input.setText(result+"");
}catch (Exception e){
e.printStackTrace();
}
}
});
tv_bind.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
bindService();
Log.e(TAG,"bindService"+iIDemoAIDLService);
}
});
}
private void bindService() {
Intent intent = new Intent();
//绑定服务端的service
intent.setAction("com.example.administrator.aidl_server.IRemoteService");
//新版本(5.0后)必须显式intent启动 绑定服务
intent.setComponent(new ComponentName("com.example.administrator.aidl_server","com.example.administrator.aidl_server.IRemoteService"));
//绑定的时候服务端自动创建
bindService(intent,conn, Context.BIND_AUTO_CREATE);
}
@Override
protected void onDestroy() {
super.onDestroy();
unbindService(conn);
}
}