大厂内部面试题:Android四大组件之一Service系列,2024年最新安卓面试资料

先自我介绍一下,小编浙江大学毕业,去过华为、字节跳动等大厂,目前阿里P7

深知大多数程序员,想要提升技能,往往是自己摸索成长,但自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!

因此收集整理了一份《2024年最新Android移动开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友。
img
img
img
img
img
img
img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上Android开发知识点,真正体系化!

由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新

如果你需要这些资料,可以添加V获取:vip204888 (备注Android)
img

正文

1.通过Binder绑定,在Binder中实现一系列的方法对Service进行操作:

2.添加一个继承Binder的内部类,并添加相应的逻辑方法 .

/** * 继承自Binder */ class MyBinder : Binder() { var bindService: BindService? = null; fun start() { bindService!!.startDownload() } fun stop() { bindService!!.stopDownload(); } }

3.重写Service的onBind方法,返回我们刚刚定义的那个内部类实例

class BindService : Service() { var binder: MyBinder? = null; override fun onCreate() { super.onCreate() binder = MyBinder(); binder!!.bindService = this; } fun startDownload() { Log.d(“BindService”, “startDownload”); } fun stopDownload() { Log.d(“BindService”, “stopDownload”); } override fun onBind(intent: Intent): IBinder { //TODO(“Return the communication channel to the service.”) return binder!! } }

4.重写ServiceConnection,onServiceConnected时调用逻辑方法 绑定服务

/** * Connection是Binder中Android进程间通信的桥梁,将IBinder对象在进程间传输 */ class BindConnection(internal var context: Context) : ServiceConnection { var binder: MyBinder? = null; var button: Button? = null; override fun onServiceConnected(name: ComponentName, service: IBinder) { this.binder = service as MyBinder Log.d(“BindService”, “onServiceConnected”) button!!.text=“绑定成功”; } override fun onServiceDisconnected(name: ComponentName) { Toast.makeText(context, “断开链接”, Toast.LENGTH_SHORT).show() } }

5.启动时进行绑定

class Main3Activity : AppCompatActivity() { var connection: BindConnection? = null; override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main3) findViewById(R.id.btn).setOnClickListener { bindIBinderService(); } findViewById(R.id.btn2).setOnClickListener { connection!!.binder!!.start(); connection!!.binder!!.stop(); } } fun bindIBinderService() { connection = BindConnection(this); connection!!.button = findViewById(R.id.btn) as Button; bindService(Intent(this, BindService::class.java), connection, Context.BIND_AUTO_CREATE); } override fun onDestroy() { super.onDestroy() unbindService(connection); } }

6.BroadCastReceive Android必读之BroadcastReceive基础

7.Messenger 在client与Server端互相绑定Messenger可以实现两端互相通信

8.在Activity中实现Messenger,绑定时将对象传到Service

/** * * @param messenger Activity中的Messenger,将此Messenger传递到Service中, * 从而使Service可以通过Messenger向Activity发送消息 * @param connection 链接的桥梁 */ class Main4Activity : AppCompatActivity() { var connection: MessengerConnection? = null; var handler = Handler(object : Handler.Callback { override fun handleMessage(msg: Message?): Boolean { when (msg!!.what) { 1 -> { Log.d(“Main4Activity”, “Receive Msg”); } else -> { } } return true; } }); var messenger: Messenger = Messenger(handler); override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main3) findViewById(R.id.btn).setOnClickListener { bindMessengerService(); } findViewById(R.id.btn2).setOnClickListener { var message: Message = Message.obtain(); message.what = 1; connection!!.messenger!!.send(message); } } fun bindMessengerService() { connection = MessengerConnection(this); connection!!.button = findViewById(R.id.btn) as Button; var intent = Intent(this, MessengerService::class.java); intent.putExtra(“Messenger”, messenger); bindService( intent, connection as ServiceConnection, Context.BIND_AUTO_CREATE ); } override fun onDestroy() { super.onDestroy() unbindService(connection as ServiceConnection); } }

9.在Service中获取Activity中的Messenger并且把自己的Messenger通过Connect传递给Activity

class MessengerService : Service() { var handler = Handler(object : Handler.Callback { override fun handleMessage(msg: Message?): Boolean { when (msg!!.what) { 1 -> { Log.d(“MessengerService”, “startDownload”); } 2 -> { Log.d(“MessengerService”, “stopDownload”); } 3, 4 -> {//同时符合3,4 } else -> { } } return true; } }); var messenger: Messenger = Messenger(handler); var activityMessenger: Messenger? = null; override fun onCreate() { super.onCreate() } override fun onBind(intent: Intent): IBinder { activityMessenger = intent.getParcelableExtra(“Messenger”); var message: Message = Message.obtain(); message.what = 1; activityMessenger!!.send(message); return messenger.binder } }

10.AIDL

1.3 介绍源码中Binder机制

答:Binder是进程间通信的具体实现,实现了IBinder接口,在BindService中接收Service中onBind(Intent intent)返回的Binder对象,通过这个Binder对象就可以对Service进行操作。这个Binder对象可以是继承自Binder类型的new出来的实例,也可以是aidl生成的AIDL.Stub对象

1.4 IntentService与Service的区别

答:IntentService是继承并处理异步请求的一个类,在IntentService内有一个工作线程来处理耗时操作,启动IntentService的方式和启动传统的Service一样,同时,当任务执行完后,IntentService会自动停止,而不需要我们手动去控制或stopSelf()。另外,可以启动IntentService多次,而每一个耗时操作会以工作队列的方式在IntentService的onHandleIntent回调方法中执行,并且,每次只会执行一个工作线程,执行完第一个再执行第二个,以此类推。推荐阅读:Android必读之IntentService

1.5 Service 是否在 main thread 中执行, service 里面是否 能执行耗时的操作?

默认情况,如果没有显示的指 service 所运行的进程, Service 和 activity 是运 行在当前 app 所在进程的 main thread(UI 主线程)里面。service 里面不能执行耗时的操作(网络请求,拷贝数据库,大文件 )特殊情况 ,可以在清单文件配置 service 执行所在的进程 ,让 service 在另 外的进程中执行

<service

android:name=“.aidl.AidlService”

android:enabled=“true”

android:process=“:AidlService”

android:exported=“true”>

android:enabled service能否被系统实例化,默认为true

android:exported service能否被隐式调用 默认为true

android:process 是否在单独的进程中,如果没有设置值,则表明此service与UI线程在同一个进程中,并且是在主线程中。如果设置值以冒号“:”开头,则表明此service是App私有的,不能被共享;如果设置的值以小写字母开头,则表明此service是可以被系统共享的。

1.6 Service的生命周期

Service 有绑定模式和非绑定模式,以及这两种模式的混合使用方式。不同 的使用方法生命周期方法也不同。

非绑定模式:当第一次调用 startService 的时候执行的方法依次为 onCreate()、onStartCommand(),当 Service 关闭的时候调用 onDestory 方 法。

绑定模式:第一次 bindService()的时候,执行的方法为 onCreate()、 onBind()解除绑定的时候会执行 onUnbind()、onDestory()。

上面的两种生命周期是在相对单纯的模式下的情形。我们在开发的过程中还 必须注意 Service 实例只会有一个,也就是说如果当前要启动的 Service 已经存 在了那么就不会再次创建该 Service 当然也不会调用 onCreate()方法。

1.7 Service 的 onStartCommand 方法有几种返回值?各代表什么意思?

有四种返回值,不同值代表的意思如下:

START_STICKY:如果 service 进程被 kill 掉,保留 service 的状态为开始状态,但不保留递送的 intent 对象。随 后系统会尝试重新创建 service,由于服务状态为开始状态,所以创建服务后一定会调用 onStartCommand(Intent,int,int)方法。如果在此期间没有任何启动命令被传递到 service,那么参数 Intent 将为 null。

START_NOT_STICKY:“非粘性的”。使用这个返回值时,如果在执行完 onStartCommand 后,服务被异常 kill 掉,系统不会自动重启该服务。

START_REDELIVER_INTENT:重传 Intent。使用这个返回值时,如果在执行完 onStartCommand 后,服务被异 常 kill 掉,系统会自动重启该服务,并将 Intent 的值传入。

START_STICKY_COMPATIBILITY: START_STICKY 的兼容版本,但不保证服务被 kill 后一定能重启。

1.8 Service 的 onRebind(Intent)方法在什么情况下会执行?

文末

当你打算跳槽的时候,应该把“跳槽成功后,我能学到什么东西?对我的未来发展有什么好处”放在第一位。这些东西才是真正引导你的关键。在跳槽之前尽量“物尽其用”,把手头上的工作做好,最好是完成了某个项目或是得到提升之后再走。跳槽不是目的,而是为了达到最终职业目标的手段

最后祝大家工作升职加薪,面试拿到心仪Offer


网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化的资料的朋友,可以添加V获取:vip204888 (备注Android)
img

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

需要这份系统化的资料的朋友,可以添加V获取:vip204888 (备注Android)*
[外链图片转存中…(img-Cgwfm7IX-1713113778006)]

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值