1、为什么要有AIDL?

不管学什么东西,最先得弄明确为什么要有这个东西。不要说存在即是合理。存在肯定合理,可是你还是没有明确。

对于AIDL有一些人的浅显概念就是,AIDL能够跨进程訪问其它应用程序,和其它应用程序通讯,那我告诉你。非常多技术都能够訪问,如广播(应用A在AndroidManifest.xml中注冊指定Action的广播)应用B发送指定Action的广播,A就能收到信息,这样也能看成不同应用之间完毕了通讯(可是这样的通讯是单向的)。还如ContentProvider,通过URI接口暴露数据给其它应用訪问;可是这样的都算不上是应用之间的通讯。

可能最让人迷惑的是Android推出来了Messager,它就是完毕应用之间的通讯的。那么为什么还要有AIDL呢。官方文档介绍AIDL中有这么一句话:

Note: Using AIDL is necessary only if you allow clients from different applications to access your service for IPC and want to handle multithreading in your service. If you do not need to perform concurrent IPC across different applications, you should create your interface by implementing a Binder or, if you want to perform IPC, but do not need to handle multithreading, implement your interface using a Messenger. Regardless, be sure that you understand Bound Services before implementing an AIDL.

第一句最重要,“仅仅有当你同意来自不同的client訪问你的服务而且须要处理多线程问题时你才必须使用AIDL”。其它情况下你都能够选择其它方法。如使用Messager,也能跨进程通讯。

可见AIDL是处理多线程、多client并发訪问的。而Messager是单线程处理。还是官方文档说的明确,一句话就能够理解为什么要有AIDL。那么是不是这样的写个AIDL试试。

2、AIDL使用

第一、定义AIDL文件
// IRemoteService.aidl
package com.example.android; // Declare any non-default types here with import statements /** Example service interface */
interface IRemoteService {
/** Request the process ID of this service, to do evil things with it. */
int getPid(); /** Demonstrates some basic types that you can use as parameters
* and return values in AIDL.
*/
void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat,
double aDouble, String aString);
}

这段代码也是官方文档的。

命名为IRemoteService.aidl。放在com.example.android包下(这个能够任意),保存后Android编译器会在gen文件夹下自己主动生成IRemoteService.java文件

第二、定义我们的服务,DDService.java,而且须要在AndroidManifest.xml中注冊,并加入“duanqing.test.aidl” 的ACTION
package com.example.service;

import com.example.android.IRemoteService;

import android.app.Service;
import android.content.Intent;
import android.os.IBinder;
import android.os.Process; public class DDService extends Service {
@Override
public void onCreate() {
super.onCreate();
System.out.println("DDService onCreate........" + "Thread: " + Thread.currentThread().getName());
}
@Override
public IBinder onBind(Intent arg0) {
System.out.println("DDService onBind");
return mBinder;
} private final IRemoteService.Stub mBinder = new IRemoteService.Stub() {
public int getPid(){
System.out.println("Thread: " + Thread.currentThread().getName());
System.out.println("DDService getPid ");
return Process.myPid();
}
public void basicTypes(int anInt, long aLong, boolean aBoolean,
float aFloat, double aDouble, String aString) {
System.out.println("Thread: " + Thread.currentThread().getName());
System.out.println("basicTypes aDouble: " + aDouble +" anInt: " + anInt+" aBoolean " + aBoolean+" aString " + aString);
}
}; }

这样我们的服务端就完毕了。把服务端执行到模拟器(或者手机上)。等一会能够看一下信息打印,重点看“线程名”


第三、实现client測试代码
新建还有一个project,相同须要加入AIDL协议文件(这是一个标准的协议文件。定义对外服务),这里我列出来我的測试代码:
package com.example.aidlclient;

import android.app.Activity;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.os.Process;
import android.os.RemoteException;
import android.view.View; import com.example.android.IRemoteService; public class MainActivity extends Activity {
private IRemoteService remoteService;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
} ServiceConnection conn = new ServiceConnection() { @Override
public void onServiceDisconnected(ComponentName name) {
} @Override
public void onServiceConnected(ComponentName name, IBinder service) {
remoteService = IRemoteService.Stub.asInterface(service);
try {
int pid = remoteService.getPid();
int currentPid = Process.myPid();
System.out.println("currentPID: " + currentPid +" remotePID: " + pid);
remoteService.basicTypes(12, 1223, true, 12.2f, 12.3, "我们的爱,我明确");
} catch (RemoteException e) {
e.printStackTrace();
}
System.out.println("bind success! " + remoteService.toString());
}
}; /**
* 监听按钮点击
* @param view
*/
public void buttonClick(View view) {
System.out.println("begin bindService");
Intent intent = new Intent("duanqing.test.aidl");
bindService(intent, conn, Context.BIND_AUTO_CREATE);
} @Override
protected void onDestroy() {
super.onDestroy();
unbindService(conn);
}
}

4、运行

点击clientbutton,运行。看信息打印:

watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvd2FuZ2R1YW5xaW5nNTk0NQ==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/Center" alt="">


看服务端打印,DDService onCreate..........Thread: main,主线程,当client调用服务端getPid方法时,服务端是在Thread: Binder2中运行,当client调用服务端basicType方法时,服务端是在Thread:Binder1中运行

彻底明确Android中AIDL及其使用的更多相关文章

  1. Android中AIDL的理解与使用(二)——跨应用绑定Service并通信

    跨应用绑定Service并通信: 1.(StartServiceFromAnotherApp)AIDL文件中新增接口: void setData(String data); AppService文件中 ...

  2. Android中AIDL的理解与使用(一)——跨应用启动/绑定Service

    AIDL(Android Interface Definition Language)--安卓接口定义语言 一.startService/stopService 1.同一个应用程序启动Service: ...

  3. Android中AIDL通信机制分析

    一.背景 ·1.AIDL出现的原因 在android系统中,每一个程序都是运行在自己的进程中,进程之间无法进行通讯,为了在Android平台,一个进程通常不能访问另一个进程的内存空间,所以要想对话,需 ...

  4. (七)Android中AIDL的应用与理解

    一.跨应用启动Service Intent serviceIntent=new Intent();serviceIntent.setComponent(new ComponentName(" ...

  5. Android 中AIDL的使用与理解

    AIDL的使用: 最常见的aidl的使用就是Service的跨进程通信了,那么我们就写一个Activity和Service的跨进程通信吧. 首先,我们就在AS里面新建一个aidl文件(ps:现在AS建 ...

  6. android中的AIDL进程间通信

    关于IPC应该不用多介绍了,Android系统中的进程之间不能共享内存,那么如果两个不同的应用程序之间需要通讯怎么办呢?比如公司的一个项目要更新,产品的需求是依附于当前项目开发一个插件,但是呢这个插件 ...

  7. Android之——AIDL深入

    转载请注明出处:http://blog.csdn.net/l1028386804/article/details/47071927 在上一篇博文<Android之--AIDL小结>中,我们 ...

  8. Android进程间通信-AIDL实现原理

    Android进程间通信基于Proxy(代理)与Stub(桩或存根)的设计模式(如图1-1所示).其中,Proxy将特殊性接口转换成通用性接口,Stub将通用性接口转换成特殊性接口,二者之间的数据转换 ...

  9. Android 中的AIDL,Parcelable和远程服务

    Android 中的AIDL,Parcelable和远程服务      早期在学习期间便接触到AIDL,当时对此的运用也是一撇而过.只到近日在项目中接触到AIDL,才开始仔细深入.AIDL的作用    ...

随机推荐

  1. Python 更新set

    更新set 由于set存储的是一组不重复的无序元素,因此,更新set主要做两件事: 一是把新的元素添加到set中,二是把已有元素从set中删除. 添加元素时,用set的add()方法: weekday ...

  2. Java之JVM调优案例分析与实战(5) - 服务器JVM进程奔溃

    环境:一个基于B/S的MIS系统,硬件为2个CPU.8GB内存的HP系统,服务器是WebLogic9.2(就是第二个案例中的那个系统).正常运行一段时间后,最近发现在运行期间频繁出现集群节点的虚拟机进 ...

  3. TCP 中的Push flag 的作用

    发送方使用该标志通知接收方将所收到的数据全部提交给接收进程.这里的数据包括接收方已经接收放在接收缓存的数据和刚刚收到的PUSH位置一的TCP报文中封装的应用数据.还是看一个简单明了的图示吧:

  4. HBase建立二级索引的一些解决方式

    HBase的一级索引就是rowkey,我们仅仅能通过rowkey进行检索. 假设我们相对hbase里面列族的列列进行一些组合查询.就须要採用HBase的二级索引方案来进行多条件的查询. 常见的二级索引 ...

  5. linux内核——会话、进程组、线程组

    会话.进程组.线程组总体关系示意图 待插入 Session(会话)与进程组 Shell 分前后台来控制的不是进程而是作业(Job)或者进程组(Process Group).一个前台作业可以由多个进程组 ...

  6. 解决在sdk manager中更新文件后出现This Android SDK requires Android Developer Toolkit version 23.1的错误

    起因:在sdksdk manager中更新了adt及其它的支持库后,eclipse报错:This Android SDK requires Android Developer Toolkit vers ...

  7. Linux下挂载硬盘分区的几种方法

    1.使用Autofs自动挂载分区 2.修改/etc/fstab 3.编写shell脚本,开机自动运行mount命令  方法一.使用Autofs  1.Autofs的特点:Autofs与Mount/Um ...

  8. centos时间调整的操作(转)

    在我们使用CentOS系统的时候,也许时区经常会出现问题,有时候改完之后还是会出错,下面我们就来学习一种方法来改变这个状况.  如果没有安装,而你使用的是 CentOS系统 那使用命令 yum ins ...

  9. C#调用windows api控制打印机 状态获取 打印 自定义纸张 完整版

    using System; using System.Text; using System.Runtime.InteropServices; using System.Security; using ...

  10. 基于Bootstrap的Asp.net Mvc 分页的实现(转)

    最近写了一个mvc 的 分页,样式是基于 bootstrap 的 ,提供查询条件,不过可以自己写样式根据个人的喜好,以此分享一下.首先新建一个Mvc 项目,既然是分页就需要一些数据,我这 边是模拟了一 ...