四大组件
安卓四大组件分别是活动(Activity),服务(Service),广播接收者(Broadcast Receive).内容提供者(Content Provider)
其作用分别是:
活动(Activity):用于表现功能
服务(Service):后台运行服务,不提供界面呈现
广播接收者(Broadcast Receive):用于接收广播
内容提供者(Content Provider):支持多个应用中存储和读取数据,相当于数据库。
Activity
Activity的生命周期
一个Activity的一生有7个生命周期,分别是:
1 | onCreate():创建activity时调用 |
当开启一个activity时,Android系统首先会回调on Create
方法,紧接着回调onstart
方法,第三个回调onResume
方法,当着三个方法回调完成之后,此时activity处于用户可见且可操作状态。当用户点击了返回键,这个activity就会被关闭,从关闭到销毁的过程中,Android系统首先会回调onpause
方法,紧接着会调用activity的onstop
方法,此时这个activity就已经被关闭了,而ondestory
方法当内存比较紧张的时候,才会执行被执行。
Activity的四种启动模式
Activity的启动模式是决定生成新的activity实例是否重用已存在的Activity实例,是否和其他Activity实例公用一个task。总共提供了四种启动模式:
standard模式
它是活动默认的启动模式,在不进行显示制定的情况下,默认使用该模式。每次激活一个activity时,都创建activity实例,并放入任务栈。
singleTop模式
如果某个Activity自己激活自己,即任务栈栈顶是该activity,则不需要创建,其余情况都要创建Activity。
singleTask模式
如果要激活的activity在任务栈中,则不需要创建,只需要把这个Activity放入栈顶,并把该Activity以上的Activity实例都出栈。
singleInstance模式
只有一个实例,并且这个实例独立运行在一个task中,这个task只有这个实例,不允许有别的Activity存在。
Activity与Activity之间的数据传递(Intent(媒介))
Activity的跳转方式
- startActivity(intent)
- startActivityForResult(intent,code)
Intent
概念:意思是一个Intent是对一个即将进行的操作的抽象,Intent的字面意识就是”意图”,Android应用程序中的三种其他应用程序基本组件——Activity, Service和Broadcast Receiver,都是使用称为intent的消息来”激活”的。
如果是两个相邻Activity之间的传值,使用intent传值
使用startActivityForResult(intent,code)实现回传值
Service
什么是Service
Android中的服务,它与Activity不同,它是不能与用户交互的,不能自己启动的,运行在后台的程序,如果我们退出应用时,Service进程并没有结束,它仍然在后台运行,那我们什么时候会用到Service呢?比如我们播放音乐的时候,有可能想边听音乐边干些其他事情,当我们退出播放音乐的应用,如果不用Service,我们就听不到歌了,所以这时候就得用到Service了,又比如当我们一个应用的数据是通过网络获取的,不同时间(一段时间)的数据是不同的这时候我们可以用Service在后台定时更新,而不用每打开应用的时候在去获取。
Service生命周期
Service的生命周期并不像Activity那么复杂,它只继承了onCreate()
,onStart()
,onDestroy()
三个方法,当我们第一次启动Service时,先后调用了onCreate(),onStart()这两个方法,当停止Service时,则执行onDestroy()方法,这里需要注意的是,如果Service已经启动了,当我们再次启动Service时,不会在执行onCreate()方法,而是直接执行onStart()方法。
StartSevice启动Service的生命周期
执行startService时,Service会经历onCreate->onStartCommand。当执行stopService时,直接调用onDestroy方法。调用者如果没有stopService,Service会一直在后台运行,下次调用者再起来仍然可以stopService。
bindService启动Service的生命周期
执行bindService时,Service会经历onCreate->onBind。这个时候调用者和Service绑定在一起。调用者调用unbindService方法或者调用者Context不存在了(如Activity被finish了),Service就会调用onUnbind->onDestroy。这里所谓的绑定在一起就是说两者共存亡了。
BroadcastReceiver
广播接收者,及是接受来自android内部的广播,对接受到的广播进行选择处理。想要接受什么样的广播和内部方法里面定义的广播匹配,匹配则进行该做的处理,没有匹配则无操作,比如在打游戏时收到短信时间,对此你要做什么操作,是想看短信内容还是什么都不做继续玩游戏,这就是广播的用途。
监听广播的步骤
- 写一个继承BroadCastReceiver的类,重写onReceive()方法,广播接收器仅在它执行这个方法时处于活跃状态。当onReceive()返回后,它即为失活状态,注意:为了保证用户交互过程的流畅,一些费时的操作要放到线程里,如类名SMSBroadcastReceiver注册该广播接收者。
- 注册有两种方法程序动态注册和AndroidManifest文件中进行静态注册(可理解为系统中注册)如下:
1 | 静态注册,注册的广播,下面的priority表示接收广播的级别"2147483647"为最高优先级 |
1 | 动态注册,一般在Activity可交互时onResume()内注册BroadcastReceiver |
Content Provider
内容提供器(Content Provider)主要用于在不同的应用程序之间实现数据共享的功能,它提供了一套完整的机制,允许一个程序访问另一个程序中的数据,同时还能保证被访数据的安全性。目前,使用内容提供器是 Android 实现跨程序共享数据的标准方式。不同于文件存储和 SharedPreferences 存储中的两种全局可读写操作模式,内容提供器可以选择只对哪一部分数据进行共享,从而保证我们程序中的隐私数据不会有泄漏的风险。
Content Provider的两种方法
1.使用现有的内容提供器来读取和操作相应程序中的数据。
2.创建自己的内容提供器给我们程序的数据提供外部访问接口。
访问其他程序中的数据
当一个应用程序通过内容提供器对其数据提供了外部访问接口,任何其他的应用程序就都可以对这部分数据进行访问。Android 系统中自带的电话簿、短信、媒体库等程序都提供了类似的访问接口。
1.ContentResolver
对于每一个应用程序来说,如果想要访问内容提供器中共享的数据,就一定要借助ContentResolve 类,可以通过 Context 中的 getContentResolver()方法获取到该类的实例。
ContentResolver 中提供了一系列的方法用于对数据进行 CRUD 操作,其中 insert()方法用于添加数据,update()方法用于更新数据,delete()方法用于删除数据,query()方法用于查询数据。但不同于 SQLiteDatabase,ContentResolver 中的增删改查方法都是不接收表名参数的,而是使用一个 Uri 参数代替,这个参数被称为内容 URI。
2.url
内容 URI 给内容提供器中的数据建立了唯一标识符,它主要由两部分组成,权限(authority)和路径(path) 。权限是用于对不同的应用程序做区分的,一般为了避免冲突,都会采用程序包名的方式来进行命名。路径则是用于对同一应用程序中不同的表做区分的,通常都会添加到权限的后面。
1 | url格式 |
存储数据的方法
sharedpreferences
sharedpreferences的概念
保存基于XML文件存储的key-value键值对数据,通常用来存储一些简单的配置信息。通过DDMS的File Explorer面板,展开文件浏览树,很明显SharedPreferences数据总是存储在
/data/data/<package name>/shared_prefs
目录下。SharedPreferences对象本身只能获取数据而不支持存储和修改,存储修改是通过SharedPreferences.edit()获取的内部接口Editor对象实现。SharedPreferences本身是一个接口,程序无法直接创建SharedPreferences实例,只能通过Context提供的getSharedPreferences(String name, int mode)方法来获取SharedPreferences实例,该方法中name表示要操作的xml文件名,第二个参数具体如下:
Context.MODE_PRIVATE: 指定该SharedPreferences数据只能被本应用程序读、写。
Context.MODE_WORLD_READABLE: 指定该SharedPreferences数据能被其他应用程序读,但不能写。
Context.MODE_WORLD_WRITEABLE: 指定该SharedPreferences数据能被其他应用程序读,写。Editor有如下主要重要方法:
SharedPreferences.Editor clear():清空SharedPreferences里所有数据
SharedPreferences.Editor putXxx(String key , xxx value): 向SharedPreferences存入指定key对应的数据,其中xxx 可以是boolean,float,int等各种基本类型据
SharedPreferences.Editor remove(): 删除SharedPreferences中指定key对应的数据项
boolean commit(): 当Editor编辑完成后,使用该方法提交修改SharedPreferences是以键值对来存储应用程序的配置信息的一种方式,它只能存储基本数据类型。一个程序的配置文件仅可以在本应用程序中使用,或者说只能在同一个包内使用,不能在不同的包之间使用。实际sharedPreferences是采用了XML格式将数据存储到设备中,在DDMS 中的File Explorer中的/data/data//shares_prefs下。
SharedPreferences对象与SQLite数据库相比,免去了创建数据库,创建表,写SQL语句等诸多操作,相对而言更加方便,简洁。但是SharedPreferences也有其自身缺陷,比如其只能存储boolean,int,float,long和String五种简单的数据类型,比如其无法进行条件查询等。所以不论SharedPreferences的数据存储操作是如何简单,它也只能是存储方式的一种补充,而无法完全替代如SQLite数据库这样的其他数据存储方式。
适用范围:保存少量的数据,且这些数据的格式非常简单:字符串型、基本类型的值。比如应用程序的各种配置信息(如是否打开音效、是否使用震动效果、小游戏的玩家积分等),解锁口令密码等。
文件存储数据
文件存储概念
文件存储是 Android 中最基本的一种数据存储方式,它不对存储的内容进行任何的格式化处理,所有数据都是原封不动地保存到文件当中的,因而它比较适合用于存储一些简单的文本数据或二进制数据。如果你想使用文件存储的方式来保存一些较为复杂的文本数据,就需要定义一套自己的格式规范,这样方便于之后将数据从文件中重新解析出来。
除此之外,Context还提供了如下几个重要的方法:
getDir(String name , int mode):在应用程序的数据文件夹下获取或者创建name对应的子目录
File getFilesDir():获取该应用程序的数据文件夹的绝对路径
String[] fileList():返回该应用数据文件夹的全部文件
文件存储数据的实现步骤
Context 类中提供了一个 openFileOutput ()方法,可以用于将数据存储到指定的文件中。这个方法接收两个参数,第一个参数是文件名,在文件创建的时候使用的就是这个名称,注意这里指定的文件名不可以包含路径,因为所有的文件都是默认存储到/data/data/<packagename>/files/
目 录 下 的 。 第 二 个 参 数 是 文 件 的 操 作 模 式 , 主 要 有 两 种 模 式 可 选 ,MODE_PRIVATE 和 MODE_APPEND。其中 MODE_PRIVATE 是默认的操作模式,表示当指定同样文件名的时候,所写入的内容将会覆盖原文件中的内容,而 MODE_APPEND 则表示如果该文件已存在就往文件里面追加内容,不存在就创建新文件。其实文件的操作模式本来还有另外两种,MODE_WORLD_READABLE 和 MODE_WORLD_WRITEABLE,这两种模式表示允许其他的应用程序对我们程序中的文件进行读写操作,不过由于这两种模式过于危险,很容易引起应用的安全性漏洞,现已在 Android 4.2 版本中被废弃。