zoukankan      html  css  js  c++  java
  • AIDL与service

    Service:Local service,一个进程中的多线程服务。

    AIDL:remote service,不同进程间通信。

    Service启动方法:

    startService():调用方destroy了那么服务不会销毁,不能与调用方直接适用,不返回任何结果。

    bindService():调用方destroy了那么服务也会销毁,能与调用方直接通信。返回Binder。

     * bindService时可以传递Binder的形式与调用方直接通信。在调用方需override叫ServiceConnnection的类来与service直接通信。

        绑定成功后通过getService()获取Service对象,将Service对象设置为null,表示绑定意外失效,Service实例不再可用。

    可以参考一下log:

    操作步骤先用startService启动服务,然后destroy。

    然后bindService绑定服务,然后destroy的结果如下:

     

    不难看出start方式启动服务时调用方销毁后服务不会自动stop。

    而bind方式绑定服务时调用方销毁后服务自动解除绑定同时销毁。

    生命周期相关:

    AIDL与service的区别

    你可以试一试创建两个包不用AIDL的情况。

     

    通过ThreadRandomServiceDemo包中的ThreadRandomServiceDemo类去开启Demo中的RandomService是可以启动的但是无法获取,

    有人会说利用bindService()不是利用可以ServiceConnection类返回Binder对象吗?是的,但是你无法加载Demo包(imorpt com.example.demo.RandomService)这样就我们无法与service直接数据交互通信了。

    但是我们利用AIDL就可以调用其他进程(或其他project)直接通信。

    AIDL是通过MyAidl.Stub.asInterface(binder);来获取binder的。

    AIDL是以获取其他进程的接口来实现IPC通信的。

    使用AIDL相关可以参考之前讲过的http://www.cnblogs.com/hongguang-kim/p/5165523.html

    简单说明一下AIDL问价自动生成的java文件中我们可以看到Parcel。

    Parcel是Android系统中应用程序进程间数据传递的容器,能够在两个进程中完成数据的打包和拆包的工作,

    但Parcel不同于通用意义上的序列化,Parcel的设计目的是用于高性能IPC传输,因此不能够将Parcel对象保存在任何持久存储设备上。

    当数据以Parcel对象的形式传递到跨进程服务的内部时,onTransact()方法将从Parcel对象中逐一的读取每个参数,然后调用Service内部制定的方法,

    并再将结果写入另一个Parcel对象,准备将这个Parcel对象返回给远程的调用者。

    自定义Parcel:

    首先建立AllResult.aidl文件,声明AllResult类

    package edu.hrbeu.ParcelMathServiceDemo;
    parcelable AllResult;
    

    在第2行代码中使用parcelable声明自定义类,这样其他的AIDL文件就可以使用这个自定义的类

    构造AllResult类。AllResult类除了基本的构造函数以外,还需要有以Parcel对象为输入的构造函数,并且需要重载打包函数writeToParcel()
    AllResult.java文件的完整代码如下

    package edu.hrbeu.ParcelMathServiceDemo;
     
    import android.os.Parcel;
    import android.os.Parcelable;
     
    public class AllResult implements Parcelable {
        public long AddResult;
        public long SubResult;
        public long MulResult;
        public double DivResult;
    .       public AllResult(long addRusult, long subResult, long mulResult, double divResult){
                                  AddResult = addRusult;
            SubResult = subResult;
            MulResult = mulResult;
            DivResult = divResult;
          }
        
          public AllResult(Parcel parcel) {
            AddResult  = parcel.readLong();
            SubResult  = parcel.readLong();
            MulResult  = parcel.readLong();
            DivResult  = parcel.readDouble();
           }
        
          @Override
        public int describeContents() {
            return 0;
        }
         @Override  
           public void writeToParcel(Parcel dest, int flags) {
                                 dest.writeLong(AddResult);34.
            dest.writeLong(SubResult);    
            dest.writeLong(MulResult);    
            dest.writeDouble(DivResult);    
          }
     
           public static final Parcelable.Creator<AllResult> CREATOR =
            new Parcelable.Creator<AllResult>(){
            public AllResult createFromParcel(Parcel parcel){
                return new AllResult(parcel);
            }
             public AllResult[] newArray(int size){
                return new AllResult[size];
                }
             };
       } 

    AllResult类继承于Parcelable
    支持通过Parcel对象实例化AllResult内容是构造函数的读取顺序。
    writeToParcel()是“打包”函数,将AllResult类内部的数据,按照特定的顺序写入Parcel对象,写入的顺序必须与构造函数的读取顺序一致
    静态公共字段Creator,用来使用Parcel对象构造AllResult对象。

    我们可以在其他类中编写如下代码:

      long addRusult = a + b;
        long subResult = a - b;
        long mulResult = a * b;
        double divResult = (double) a / (double)b;
        AllResult allResult = new AllResult(addRusult, subResult, mulResult, divResult);

    我们可以通过result.AddResult变量获取其运算结果。

  • 相关阅读:
    《Entity Framework 6 Recipes》中文翻译系列 (6) -----第二章 实体数据建模基础之使用Code First建模自引用关系 (转)
    《Entity Framework 6 Recipes》翻译系列 (5) -----第二章 实体数据建模基础之有载荷和无载荷的多对多关系建模 (转)
    《Entity Framework 6 Recipes》翻译系列 (4) -----第二章 实体数据建模基础之从已存在的数据库创建模型 (转)
    《Entity Framework 6 Recipes》翻译系列 (3) -----第二章 实体数据建模基础之创建一个简单的模型 (转)
    《Entity Framework 6 Recipes》翻译系列(2) -----第一章 开始使用实体框架之使用介绍 (转)
    《Entity Framework 6 Recipes》翻译系列 (1) -----第一章 开始使用实体框架之历史和框架简述 (转)
    EF——使用Data Annotations和Fluent API配置数据库的映射配置 02.01(转)
    EF——一个实体对应两张表,两个实体对应一张表 06 (转)
    EF——继承映射关系TPH、TPT和TPC的讲解以及一些具体的例子 05 (转)
    EF——一对一、一对多、多对多关系的配置和级联删除 04(转)
  • 原文地址:https://www.cnblogs.com/hongguang-kim/p/5622767.html
Copyright © 2011-2022 走看看