Android面试题

总结各种关于android的面试题 —— 汇总篇

1、简述Activity的生命周期

       Onreate()创建时,OnStart()启动OnResume()与用户交互时调用,onReStart()activity再次启动之前调用 onPause()当前activity暂停,另一个activity启动时调用,Onstop()当activity变的不可见时调用,onDestory()当activity被销毁之前调用

2、对象Object读写的是哪两个流

   objectinputstream  objectoutputstream

3、你对Android系统的看法;说说他的优缺点

   这个木有写

4、Intent启动Activity有几种方式,请分别简述

    三种,一种是用类直接调用,二是用包名加类名调用  三是 action隐身调用

5、ListView怎么处理大量的加载数据;比如有10万条数据,你在ListView怎么处理,你不可能一条一条的的往下拉

   这个卡住了 怎么搞;俺搞错了他的意思,我说要数据不一次性加载,可以根据手机的屏幕大小拉几条数据,然后需要往下拉的时候再来到服务器取数据;其实的他的意思是

比如拉了10万条这10万条怎么处理,你是拉几条数据然后把这前几天数据释放了,还是一直在屏幕上,一直在的屏幕上的数据怎么处理,ListView数据一多响应程序性能  哥瞬间蛋碎了,哪个傻逼会一直拉10万条数据 一直往下拉看啊; 没办法回家 百度

6、简述Android应用结构

   俺直接写了代码块、资源文件、androidmanifest.xml

7、怎么停止activity,多个Activity怎么安全的退出

8、ContentValues和map相似,key是不是任意类型,value是不是任意类型

     (这个 哥还真木有注意啊)节操又碎了啊

     key是string类型,value是基本类型

9、android中常用的布局哪几种,请简述

 线性布局、相对布局、表格布局、贞布局、绝对布局

10、请说说ContentProvider怎么实现数据共享。

  哥写的简单明了 定一个ContentProvider的之类,实现父类的增删改查的方法,然后在androidmanifest.xml( 这个英文不会写 我直接用主配置文件来代替 估计面试官看的蛋疼 )文件中注册,并绑定一个uri将数据暴露出来;需要获取数据方通过获取ContentResolver的方法来调用

11、Service怎么启动和停止,有几种

两种  startService、stopService、bindService、unbindService(哥记得这个好像解除了与service的绑定 service好像没有停止)

12、activity怎么设置成窗口模式

android:theme="android:stype/Theme.Dialog" 

这是今天面试的的一家上海公司 搞支付的  记得的android就这么多,还有样式 、SQL语句等等

Java基础部分

1.谈谈hashmap和hashtable的区别,如何去遍历一个map

答:

Hashtable继承了Dictionary,是线程安全的,键值对中不能出现null。

Hashmap实现了Map接口,是Hashtable的轻量级实现(非线程安全的实现),即多个线程访问Hashmap时需要为其准备外同步,且Hashmap的键、值均可以为null。

遍历map有两种方式:keyset(效率低)和entryset(效率高),两种方式都需要创建Iterator迭代器对象,不同的是使用keyset需要从迭代器中获取map的key,并且通过key获取value(key=iterator.next(); value=map.get(key));使用entryset则需要从迭代器中获取Map.Entry对象,再从中获取map的key和value(Map.Entry entry=(Map.Entry)iterator.next(); key=entry.getKey(); value=entry.getValue())。

Map map=new HashMap();

Iterator iterator=map.entrySet().iterator();

while(iterator.hasNext()){

  Map.Entry entry=(Map.Entry)iterator.next();

  Object key=entry.getKey();

  Object value=entry.getValue();

}

Map map=new HashMap();

Iterator iterator=map.keySet().iterator();

while(iterator.hasNext){

  Object key=iterator.next();

  Object value=map.get(key);

}

2.说出线程同步的几个方法

答:

synchronized同步代码块:synchronized(同步监视器){…}

synchronized修饰的同步方法:public synchronized 返回值 方法名(){…}

wait();:wait方法必须在用有synchronized修饰的地方才能使用

notify();:唤醒了有相同同步监视器的wait(),从wait()的下一行代码开始执行

notifyAll();:唤醒了所有调用wait()的方法

3. java中char占几个字节,为什么

答: 2个字节。java是采用unicode编码,使用16位的编码空间,即每个字符都占两个字节

4. try{}里有一个return语句,那么紧跟在这个try后的finally{}里的code会不会被执行?什么时候被执行?在return之前还是之后

答:会被执行,在return之后执行,finally{}中的语句只有在虚拟机停止的情况下才不执行。

Android基础部分

1. 假设activity所有的生命周期函数里都已经调用了标准输出,比如,当Activity的onCreate被调用时,会输出:A->onCreate();那么当Activity A跳转至Activity B时,写出此时的输出结果

答:

//A->onCreate();

//A->onStart(); 

//A->onResume();  

B->onCreate();  

B->onStart(); 

B->onResume();  

A->onPause();

2.启动service有几种方式,说出他们之间的主要区别

答:

调用startService():通过此种方法启动的service会一直运行在后台直到stopService()或stopSelf()方法被调用。

调用bindService():通过此种方法启动的service会与调用者绑定,如果这个service还没有被启动,那么service启动时将不会调用onStart(),只调用onCreate()和onBind(),调用者被销毁时,service也被销毁

3. intent.putExtra时,如果传递的不是基本类型,而是一个”Object”,那么对这个对象有什么要求?还是说任何对象都可以进行传递?

答:

必须实现Serializable接口,实现CharSequence接口或者实现Parcelable接口的对象才可以进行传递。

  

4.当调用startActivityForResult时,如何获取并处理返回的结构

答:

通过onActivityResult(int requestCode, int resultCode, Intent data)处理返回的数据

requestCode:调用startActivityForResult(Intent intent, int requestCode)时传递过去的请求码。

resultCode:被调用的Activity执行setResult(int resultCode, Intent intent)时传递的结果码,一般有RESULT_CANCELED,RESULT_OK等,用于区分被调用的Activity传回的不同结果

data:被调用的Activity传回来的数据,可以用data.getExtras()得到数据,用Bundle类型的变量来接收,调用get…(String key)来获取对应的值

5. 谈谈ContentProvider如何跟URI关联到一起的

答:在AndroidManifest.xml的ContentProvider标签中添加uri标签来使他们关联起来  

6.  当使用CursorAdapter的时候,如何将Cursor交给Activity自己去管理?即由系统根据Activity的生命周期来管理cursor是否关闭和释放

答:Activity的生命周期来管理cursor是否关闭和释放

让我们的activity 继承自listActivity,调用它的startManagingCursor(Cursor c);  来管理得到的游标。

7.  说出IntentFilter中的<action android:name=”android.intent.action.MAIN”/>和<category android:name=”android.intent.category.LAUNCHER”/>的用途

答:android.intent.action.MAIN决定应用程序最先启动的Activity 。android.intent.category.LAUNCHER决定应用程序是否显示在程序列表里。Main ,LAUNCHER同时设定才有意义,

8.  谈谈Handler的用途,并说出它和Looper, HandlerThread的一些关系

Handler在android里负责发送和处理消息。它的主要用途:

答: Handler:

1)按计划发送消息或执行某个Runnanble(使用POST方法),类似定时器;

2)从其他线程中发送来的消息放入消息队列中,避免线程冲突(常见于更新UI线

程);

默认情况下,Handler接受的是当前线程下的消息循环实例(使用Handler(Looper 

looper)、Handler(Looper looper, Handler.Callback callback)可以指定线程),同时一个

消息队列可以被当前线程中的多个对象进行分发、处理(在 UI线程中,系统已经

有一个Activity来处理了,你可以再起若干个Handler来处理)。在实例化Handler的

时候,Looper可以是任意 线程的,只要有Handler的指针,任何线程也都可以

sendMessage。Handler对于Message的处理不是并发的。一个Looper 只有处理完一

条Message才会读取下一条,所以消息的处理是阻塞形式的(handleMessage()方法

里不应该有耗时操作,可以将耗时操作放在 其他线程执行,操作完后发送Message

(通过sendMessges方法),然后由handleMessage()更新UI)。

1. 如何去通知ListView去更新视图?如何通知一个普通View去更新视图?9

答:1. 调用Adapter的notifyDatasetChanged方法通知ListView更新显示

2. 在Android的布局体系中,父View负责刷新、布局显示子View;而当子View需要刷新时,则是通知父View来完成。

步骤就是:

1、调用子View的invalidate()

2、跳转到上一层的invalidateChild函数中区

3、在一次调用invalidateChildInParent的函数一次层层刷新

2. 如何设置应用程序是否支持横竖屏切换?如果可以切换,那么如何避免每次切换的时候不会重复调用onCreate函数呢

答:

1. 横竖屏切换

如果要让软件在横竖屏之间切换,由于横竖屏的高宽会发生转换,有可能会要求不同的布局。可以通过以下两种方法来切换布局:

1)在res目录下建立layout-land和layout-port目录,相应的layout文件名不变,比如main.xml。 layout-land是横屏的layout,layout-port是竖屏的layout,其他的不用管,横竖屏切换时程序为调用Activity的 onCreate方法,从而加载相应的布局。

2)假如布局资源不按照如上设置,则可以通过java代码来判断当前是横屏还是竖屏然后来加载相应的xml布局文件。因为当屏幕变为横屏的时候,系统会重新呼叫当前Activity的onCreate方法,你可以把以下方法放在你的onCreate中来检查当前的方向,然后可以让你的setContentView来载入不同的layout xml。

2:如果不想让软件在横竖屏之间切换,最简单的办法就是在项目的AndroidManifest.xml中找到你所指定的activity中加上android:screenOrientation属性,他有以下几个参数:

"unspecified":默认值 由系统来判断显示方向.判定的策略是和设备相关的,所以不同的设备会有不同的显示方向. 
"landscape":横屏显示(宽比高要长) 
"portrait":竖屏显示(高比宽要长) 
"user":用户当前首选的方向 
"behind":和该Activity下面的那个Activity的方向一致(在Activity堆栈中的) 
"sensor":有物理的感应器来决定。如果用户旋转设备这屏幕会横竖屏切换。 
"nosensor":忽略物理感应器,这样就不会随着用户旋转设备而更改了("unspecified"设置除外)。

也可以在JAVA代码中设置

setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE)来设置。

通过查阅Android API可以得知android:onConfigurationChanged实际对应的是Activity里的 onConfigurationChanged()方法。在AndroidManifest.xml中添加上诉代码的含义是表示在改变屏幕方向、弹出软件盘和隐藏软键盘时,不再去执行onCreate()方法,而是直接执行onConfigurationChanged()。如果不申明此段代码,按照 Activity的生命周期,都会去执行一次onCreate()方法,而onCreate()方法通常会在显示之前做一些初始化工作。所以如果改变屏幕 方向这样的操作都去执行onCreate()方法,就有可能造成重复的初始化

Android面试选择题

  

1. 下列哪些语句关于内存回收的说明是正确的? (b ) 

    A、 程序员必须创建一个线程来释放内存

  B、 内存回收程序负责释放无用内存

  C、 内存回收程序允许程序员直接释放内存

  D、 内存回收程序可以在指定的时间释放内存对象

2. 下面异常是属于Runtime Exception 的是(abcd)(多选) 

    A、ArithmeticException

  B、IllegalArgumentException

  C、NullPointerException

  D、BufferUnderflowException

3. Math.round(11.5)等于多少(). Math.round(-11.5)等于多少(c). c 

    A、11 ,-11    B、11 ,-12    C、12 ,-11    D、12 ,-12

4. 下列程序段的输出结果是:(b )

  void complicatedexpression_r(){

  int x=20, y=30;

  boolean b;

  b=x>50&&y>60||x>50&&y<-60||x<-50&&y>60||x<-50&&y<-60;

  System.out.println(b);

  }

  A、true    B、false    C、1    D、011.activity

5. 对一些资源以及状态的操作保存,最好是保存在生命周期的哪个函数中进行(d)

    A、onPause() B、onCreate() C、 onResume() D、onStart()

6. Intent传递数据时,下列的数据类型哪些可以被传递(abcd)(多选) 

    A、Serializable   B、charsequence    C、Parcelable  D、Bundle

7. android 中下列属于Intent的作用的是(c) 

    A、实现应用程序间的数据共享

  B、是一段长的生命周期,没有用户界面的程序,可以保持应用在后台运行,而不会因为切换页面而消失

  C、可以实现界面间的切换,可以包含动作和动作数据,连接四大组件的纽带

  D、处理一个应用程序整体性的工作

8. 下列属于SAX解析xml文件的优点的是(b) 

    A、将整个文档树在内存中,便于操作,支持删除,修改,重新排列等多种功能

  B、不用事先调入整个文档,占用资源少

  C、整个文档调入内存,浪费时间和空间

  D、不是长久驻留在内存,数据不是持久的,事件过后,若没有保存数据,数据就会

  消失

9. 下面的对自定style的方式正确的是

   A、 <resources>
       <style name="myStyle">
       <itemname="android:layout_width">fill_parent</item>
       </style>
       </resources>
   B、 <style name="myStyle">
       <itemname="android:layout_width">fill_parent</item>
        </style>
   C、 <resources>
       <itemname="android:layout_width">fill_parent</item>
       </resources>
   D、 <resources>
       <stylename="android:layout_width">fill_parent</style>
       </resources>

  10. 在android中使用Menu时可能需要重写的方法有(ac)。(多选) A、onCreateOptionsMenu()

  B、onCreateMenu()

  C、onOptionsItemSelected()

  D、onItemSelected()

  11. 在SQL Server Management Studio 中运行下列T-SQL语句,其输出值(c)。 SELECT @@IDENTITY

  A、 可能为0.1

  B、 可能为3

  C、 不可能为-100

  D、 肯定为0

12. 在SQL Server 2005中运行如下T-SQL语句,假定SALES表中有多行数据,执行查询之 后的结果是(d)。 

BEGIN TRANSACTION A

  Update SALES Set qty=30 WHERE qty<30

  BEGIN TRANSACTION B

  Update SALES Set qty=40 WHEREqty<40

  Update SALES Set qty=50 WHEREqty<50

  Update SALES Set qty=60 WHEREqty<60

  COMMIT TRANSACTION B

  COMMIT TRANSACTION A

  A、SALES表中qty列最小值大于等于30

  B、SALES表中qty列最小值大于等于40

  C、SALES表中qty列的数据全部为50

  D、SALES表中qty列最小值大于等于60

13. 在android中使用SQLiteOpenHelper这个辅助类时,可以生成一个数据库,并可以对数据库版本进行管理的方法可以是(ab)

    A、getWriteableDatabase()

  B、getReadableDatabase()

  C、getDatabase()

  D、getAbleDatabase()

14. android 关于service生命周期的onCreate()和onStart()说法正确的是(ad)(多选题) 

A、当第一次启动的时候先后调用onCreate()和onStart()方法

  B、当第一次启动的时候只会调用onCreate()方法

  C、如果service已经启动,将先后调用onCreate()和onStart()方法

  D、如果service已经启动,只会执行onStart()方法,不在执行onCreate()方法

15. 下面是属于GLSurFaceView特性的是(abc)(多选)

    A、管理一个surface,这个surface就是一块特殊的内存,能直接排版到android的视图view上。

  B、管理一个EGL display,它能让opengl把内容渲染到上述的surface上。

  C、让渲染器在独立的线程里运作,和UI线程分离。

  D、可以直接从内存或者DMA等硬件接口取得图像数据

  16. 下面在AndroidManifest.xml文件中注册BroadcastReceiver方式正确的

A、<receiver android:name="NewBroad">
 <intent-filter>
 <action 
 android:name="android.provider.action.NewBroad"/>
 <action>
 </intent-filter>
 </receiver>
 B、<receiver android:name="NewBroad">
 <intent-filter>
 android:name="android.provider.action.NewBroad"/>
 </intent-filter>
 </receiver>
 C、<receiver android:name="NewBroad">
 <action 
 android:name="android.provider.action.NewBroad"/>
 <action>
 </receiver>
 D、<intent-filter>
 <receiver android:name="NewBroad">
 <action>
 android:name="android.provider.action.NewBroad"/>
 <action>
 </receiver>
</intent-filter>

17. 关于ContenValues类说法正确的是(a) 

    A、他和Hashtable比较类似,也是负责存储一些名值对,但是他存储的名值对当中的

  名是String类型,而值都是基本类型

  B、他和Hashtable比较类似,也是负责存储一些名值对,但是他存储的名值对当中的

  名是任意类型,而值都是基本类型

  C、他和Hashtable比较类似,也是负责存储一些名值对,但是他存储的名值对当中的

  名,可以为空,而值都是String类型

  D、他和Hashtable比较类似,也是负责存储一些名值对,但是他存储的名值对当中

  的名是String类型,而值也是String类型

18. 我们都知道Hanlder是线程与Activity通信的桥梁,如果线程处理不当,你的机器就会变得越慢,那么线程销毁的方法是(a)

A、onDestroy()

  B、onClear()

  C、onFinish()

  D、onStop()

19. 下面退出Activity错误的方法是(c)

A、finish()

  B、抛异常强制退出

  C、System.exit()

  D、onStop()

20. 下面属于android的动画分类的有(ab)(多项) 

      A、Tween    B、Frame    C、Draw   D、Animation

21. 下面关于Android dvm的进程和Linux的进程,应用程序的进程说法正确的是(d) 

A、DVM指dalivk的虚拟机.每一个Android应用程序都在它自己的进程中运行,不一定拥有一个独立的Dalvik虚拟机实例.而每一个DVM都是在Linux中的一个进程,所以说可以认为是同一个概念.

  B、DVM指dalivk的虚拟机.每一个Android应用程序都在它自己的进程中运行,不一定拥有一个独立的Dalvik虚拟机实例.而每一个DVM不一定都是在Linux中的一个进程,所以说不是一个概念.

  C、DVM指dalivk的虚拟机.每一个Android应用程序都在它自己的进程中运行,都拥有一个独立的Dalvik虚拟机实例.而每一个DVM不一定都是在Linux中的一个进程,所以说不是一个概念.

  D、DVM指dalivk的虚拟机.每一个Android应用程序都在它自己的进程中运行,都拥有一个独立的 Dalvik虚拟机实例.而每一个DVM都是在Linux中的一个进程,所以说可以认为是同一个概念.

22. Android项目工程下面的assets目录的作用是什么b

A、放置应用到的图片资源。

  B、主要放置多媒体等数据文件

  C、放置字符串,颜色,数组等常量数据

  D、放置一些与UI相应的布局文件,都是xml文件

23. 关于res/raw目录说法正确的是(a)

A、 这里的文件是原封不动的存储到设备上不会转换为二进制的格式

  B、这里的文件是原封不动的存储到设备上会转换为二进制的格式

  C、 这里的文件最终以二进制的格式存储到指定的包中

  D、这里的文件最终不会以二进制的格式存储到指定的包中

  24. 下列对android NDK的理解正确的是(abcd )A、 NDK是一系列工具的集合

  B、 NDK 提供了一份稳定、功能有限的 API 头文件声明。

  C、 使 “Java+C” 的开发方式终于转正,成为官方支持的开发方式

D、 NDK 将是 Android 平台支持 C 开发的开端

二、Android面试填空题

25. android中常用的四个布局是framlayout,linenarlayout,relativelayout和tablelayout。

26. android 的四大组件是activiey,service,broadcast和contentprovide。

27. java.io包中的objectinputstream和objectoutputstream类主要用于对对象(Object)的读写。

28. android 中service的实现方法是:startservice和bindservice。

29. activity一般会重载7个方法用来维护其生命周期,除了 onCreate(),onStart(),onDestory() 外还有onrestart,onresume,onpause,onstop。

30. android的数据存储的方式sharedpreference,文件,SQlite,contentprovider,网络。

31. 当启动一个Activity并且新的Activity执行完后需要返回到启动它的Activity来执行 的回调函数是startActivityResult()。

32. 请使用命令行的方式创建一个名字为myAvd,sdk版本为2.2,sd卡是在d盘的根目录下,名字为scard.img, 并指定屏幕大小HVGA.____________________________________。  

33. 程序运行的结果是:_____good and gbc__________。 public classExample{

  String str=new String("good");

  char[]ch={'a','b','c'};

  public static void main(String args[]){

  Example ex=new Example();

  ex.change(ex.str,ex.ch);

  System.out.print(ex.str+" and ");

  Sytem.out.print(ex.ch);

  }

  public void change(String str,char ch[]){

  str="test ok";

  ch[0]='g';

  }

  }

1. android dvm 的进程和Linux的进程,应用程序的进程是否为同一个概念:

答:dvm是dalivk虚拟机。每一个android应用程序都在自己的进程中运行,都拥有一个dalivk虚拟机实例。而每一个dvm都是在linux的一个进程。所以说可以认为是同一个概念。

2.android的动画有哪几种?他们的特点和区别是什么?

答:两种,一种是tween动画,一种是frame动画。tween动画,这种实现方式可以使视图组件移动,放大或缩小以及产生透明度的变化。frame动画,传统的动画方法,通过顺序的播放排列好的图片来实现,类似电影。

3.handler进制的原理:

答:android提供了handler和looper来满足线程间的通信。Handler先进先出原则。looper用来管理特定线程内对象之间的消息交换(message Exchange).

 1)  looper:一个线程可以产生一个looper对象,由它来管理此线程里的message queue(消息队列)

 2)  handler:你可以构造一个handler对象来与looper沟通,以便push新消息到messagequeue里;或者接收looper(从messagequeue里取出)所送来的消息。

 3)  messagequeue:用来存放线程放入的消息。

 4)  线程:UI thread 通常就是main thread,而android启动程序时会为它建立一个message queue.

4.android view的刷新:

答:android中对View的更新有很多种方式,使用时要区分不同的应用场合。我感觉最要紧的是分清:多线程和双缓冲的使用情况。
 1).不使用多线程和双缓冲
 这种情况最简单了,一般只是希望在View发生改变时对UI进行重绘。你只需在Activity中显式地调用View对象中的invalidate()方法即可。系统会自动调用 View的onDraw()方法。
 2).使用多线程和不使用双缓冲
 这种情况需要开启新的线程,新开的线程就不好访问View对象了。强行访问的话会报:android.view.ViewRoot$CalledFromWrongThreadException:Only the originalthread that created a view hierarchy can touch its views.
    这时候你需要创建一个继承了android.os.Handler的子类,并重写handleMessage(Messagemsg)方法。android.os.Handler是能发送和处理消息的,你需要在Activity中发出更新UI的消息,然后再你的Handler(可以使用匿名内部类)中处理消息(因为匿名内部类可以访问父类变量,你可以直接调用View对象中的invalidate()方法 )。也就是说:在新线程创建并发送一个Message,然后再主线程中捕获、处理该消息
 3).使用多线程和双缓冲
 Android中SurfaceView是View的子类,她同时也实现了双缓冲。你可以定义一个她的子类并实现SurfaceHolder.Callback接口。由于实现SurfaceHolder.Callback接口,新线程就不需要android.os.Handler帮忙了。SurfaceHolder中lockCanvas()方法可以锁定画布,绘制玩新的图像后调用unlockCanvasAndPost(canvas)解锁(显示),还是比较方便得。

5.说说mvc模式的原理,它在android中的运用:

答:android的官方建议应用程序的开发采用mvc模式。何谓mvc?

mvc是model,view,controller的缩写,mvc包含三个部分:
l模型(model)对象:是应用程序的主体部分,所有的业务逻辑都应该写在该层。
2视图(view)对象:是应用程序中负责生成用户界面的部分。也是在整个mvc架构中用户唯一可以看到的一层,接收用户的输入,显示处理结果。

3控制器(control)对象:是根据用户的输入,控制用户界面数据显示及更新model对象状态的部分,控制器更重要的一种导航功能,想用用户出发的相关事件,交给m哦得了处理。

 android鼓励弱耦合和组件的重用,在android中mvc的具体体现如下:

 1) 视图层(view):一般采用xml文件进行界面的描述,使用的时候可以非常方便的引入,当然,如何你对android了解的比较的多了话,就一定 可以想到在android中也可以使用javascript+html等的方式作为view层,当然这里需要进行java和javascript之间的通 信,幸运的是,android提供了它们之间非常方便的通信实现。

 2) 控制层(controller):android的控制层的重 任通常落在了众多的acitvity的肩上,这句话也就暗含了不要在acitivity中写代码,要通过activity交割model业务逻辑层处理, 这样做的另外一个原因是android中的acitivity的响应时间是5s,如果耗时的操作放在这里,程序就很容易被回收掉。

 3) 模型层(model):对数据库的操作、对网络等的操作都应该在model里面处理,当然对业务计算等操作也是必须放在的该层的。
6.Activity的生命周期:

答:onCreate: 在这里创建界面,做一些数据 的初始化工作

  onStart: 到这一步变成用户可见不可交互的

  onResume:变成和用户可交互 的,(在activity 栈系统通过栈的方式管理这些个Activity的最上面,运行完弹出栈,则回到上一个Activity)

  onPause: 到这一步是可见但不可交互的,系统会停止动画 等消耗CPU 的事情从上文的描述已经知道,应该在这里保存你的一些数据,因为这个时候你的程序的优先级降低,有可能被系统收回。在这里保存的数据,应该在

  onstop: 变得不可见,被下一个activity覆盖了

  onDestroy: 这是activity被干掉前最后一个被调用方法了,可能是外面类调用finish方法或者是系统为了节省空间将它暂时性的干掉
7.让Activity变成一个窗口:

答:Activity属性设定:有时候会做个应用程序是漂浮在手机主界面的。这个只需要在设置下Activity的主题theme,即在Manifest.xml定义Activity的地方加一句:

android :theme="@android:style/Theme.Dialog"
如果是作半透明的效果:

android:theme="@android:style/Theme.Translucent"
8.Android中常用的五种布局:

答:LinearLayout线性布局;AbsoluteLayout绝对布局;TableLayout表格布局;RelativeLayout相对布局;FrameLayout帧布局;
9.Android的五种数据存储方式:

答:sharedPreferences;文件;SQLite;contentProvider;网络
10.请解释下在单线程模型中Message、Handler、Message Queue、Looper之间的关系:

答:Handler获取当前线程中的looper对象,looper用来从存有Message的Message Queue里取出message,再由Handler进行message的分发和处理。


11.AIDL的全称是什么?如何工作?能处理哪些类型的数据?

答:AIDL(AndroidInterface Definition Language)android接口描述语言
12.系统上安装了多种浏览器,能否指定某浏览器访问指定页面?请说明原由:

答:通过直接发送Uri把参数带过去,或者通过manifest里的intentfilter里的data属性。代码如下:
 Intent intent = new Intent();

Intent.setAction(“android.intent.action.View”);

Uri uriBrowsers = Uri.parse(“http://www.sina.com.cn”);

Intent.setData(uriBrowsers);

//包名、要打开的activity
intent.setClassName(“com.android.browser”,”com.android.browser.BrowserActivity”);

startActivity(intent);
13.什么是ANR,如何避免?

答:ANR的定义:

在android上,如果你的应用程序有一段时间响应不移灵敏,系统会向用户提示“应用程序无响应”(ANR:application Not Responding)对话框。因此,在程序里对响应性能的设计很重要,这样,系统不会显示ANR给用户。

如何避免:

首先来研究下为什么它会在android的应用程序里发生和如何最佳构建应用程序来避免ANR.
 android应用程序通常是运行在一个单独的线程(例如:main)里,这就意味你的应用程序所做的事情如果在主线程里占用了大长时间的话,就会引发ANR对话框,因为你的应用程序并没有给自己机会来处理输入事件或者Intent广播。

 因此,运行在主线程里的任何访求都尽可能少做事情。特别是,activity应该在它的关键生命周期方法(onCreate()和onResume())里尽可能少的去作创建操作。潜在的耗时操作,例如网络或数据库操作,或者高耗时的计算如改变位图尺寸,应该在子线程里(或者以数据库操作为例,通过异步请求的方式)来完成。然而,不是说你的主线程阻塞在那里等待子线程的完成---也不是调用Thread.wait()或者Thread.sleep()。替代的方法是:主线程应该为子线程提供一个Handler,以便完成时能够提交给主线程。以这种方式设计你的应用程序,将能保证你的主线程保持对输入的响应性并能避免由5秒输入事件的超时引发的ANR对话框。这种做法应该在其它显示UI的线程里效仿,因为它们都受相同的超时影响。

 IntentReceiver执行时间的特殊限制意味着它应该做:在后台里做小的、琐碎的工作,如保存设定或注册一个Notification。和在主线程里调用的其它方法一样,应用程序应该避免在BroadcastReceiver里做耗时的操作或计算,但也不是在子线程里做这些任务(因为BroadcastReceiver的生命周期短),替代的是,如果响应Intent广播需要执行一个耗时的动作的话,应用程序应该启动一个Service。顺便提及一句,你也应该避免在Intent Receiver里启动一个Activity,因为它会创建一个新的画面,并从当前用户正在运行的程序上抢夺焦点。如果你的应用程序在响应Intent广播时需要向用户展示什么,你应该使用Notification Manager来实现。

 一般来说,在应用程序里,100到200ms是用户能感知阻滞的时间阈值,下面总结了一些技巧来避免ANR,并有助于让你的应用程序看起来有响应性。

 如果你的应用程序为响应用户输入正在后台工作的话,可以显示工作的进度(ProgressBar和ProgressDialog对这种情况来说很有用)。特别是游戏,在子线程里做移动的计算。如果你的程序有一个耗时的初始化过程的话,考虑可以显示一个Splash Screen或者快速显示主画面并异步来填充这些信息。在这两种情况下,你都应该显示正在进行的进度,以免用户认为程序被冻结了。
14.什么情况会导致Force Close?如何避免?能否捕获导致其的异常?

答:如空指针等可以导致ForceClose;可以看Logcat,然后找到对应的程序代码来解决错误。
15.横竖屏切换时候的activity的生命周期:

答:1) 新建一个activity,并把各个生命周期打印出来

   2) 运行activity,得到如下信息:

            onCreate()onStart()onResume()

   3) 按ctrl+F12切换成横屏时

     onSaveInstanceState()onPause()onStop()onDestroy()onCreate()、   

     onStart()onRestoreInstanceState()onResume()

    4) 再按ctrl+f12切换成竖屏时,发现打印了两次相同的Log

 onSaveInstanceState()onPause()onStop()onDestroyonCreate()onStart()onRestoreInstanceState()onResume()

 onSaveInstanceState()onPause()onStop()onDestroyonCreate()onStart()onRestoreInstanceState()onResume()

 5) 修改AndroidManifest.xml,把该Activity添加android:configChanges=“orientation”,执行步骤3

 onSaveInstanceState() ---- onPause() ----onStop() ---- onDestroy() ---- onCreate() ---- onStart() ---- onRestoreInstanceState() ---- onResume()

 6) 修改AndroidManifest.xml,把该Activity添加android:configChanges=“orientation”,执行步骤4,发现不会再打印相同信息,但多打印了一行onConfigChanged

 onSaveInstanceState() ---- onPause() ---- onStop() ---- onDestroy() ---- onCreate() ---- onStart() ---- onRestoreInstanceState() ----- onResume() ----onConfigurationChanged()

 7) 把步骤5的android:configChanges=“orientation”改成

android:configChanges=“orientation|keyboradHidden”,执行步骤3,就只打印onConfigChanged

 onConfigurationChanged()

 8) 把步骤5的android:configChanges=“orientation”改成

android:configChanges=“orientation|keyboradHidden”,执行步骤4

 onConfigurationChanged()

 onConfigurationChanged()

 总结:

1) 不设置activity的android:configChanges时,切屏会重新调用各个生命周期,切横屏时会执行一次,切竖屏时会执行两次。

2) 设置activity的android:configChanges=“orientation”时, 切屏会重新调用各个生命周期,切横屏、竖屏时都只会执行一次,但是竖屏最后多打印一条onConfigurationChanged()

3) 设置activity的android:configChanges=“orientation|keyboardHidden”时,切屏不会重新调用各个生命周期,只会执行onConfigurationChanged(),横屏一次,竖屏两次

再总结下整个activity的生命周期:

1) 当前activity产生事件弹出Toast和AlertDialog的时候Activity的生命周期不会有改变

2) Activity运行时按下HOME键(跟被完全覆盖一样的)

onSavaInstanceState === onPause === onStop === onRestart === onStart === onResume

 3) 未被完全覆盖,只是失去焦点:

 onPause ===onResume
16.如何将SQLite数据库(.db文件)与apk文件一起发布?

答:可以将.db文件复制到Eclipse Android工程中的res aw目录中。所有在res aw目录中的文件不会被压缩,这样可以直接提取该目录中的文件。可以将.db文件复制到res aw目录中
17.如何将打开res aw目录中的数据库文件?

答:在Android中不能直接打开res aw目录中的数据库文件,而需要在程序第一次启动时将该文件复制到手机内存或SD卡的某个目录中,然后再打开该数据库文件。复制的基本方法是使用getResources().openRawResource方法获得res aw目录中资源的 InputStream对象,然后将该InputStream对象中的数据写入其他的目录中相应文件中。在Android SDK中可以使用SQLiteDatabase.openOrCreateDatabase方法来打开任意目录中的SQLite数据库文件。
18.android 中有哪几种解析xml的类?官方推荐哪种?以及它们的原理和区别:

答:XML解析主要有三种方式,SAX、DOM、PULL。常规在PC上开发我们使用Dom相对轻松些,但一些性能敏感的数据库或手机上还是主要采用SAX方 式,SAX读取是单向的,优点:不占内存空间、解析属性方便,但缺点就是对于套嵌多个分支来说处理不是很方便。而DOM方式会把整个XML文件加载到内存 中去,这里Android开发网提醒大家该方法在查找方面可以和XPath很好的结合如果数据量不是很大推荐使用,而PULL常常用在J2ME对于节点处 理比较好,类似SAX方式,同样很节省内存,在J2ME中我们经常使用的KXML库来解析。
19.DDMS和TraceView的区别?

答:DDMS是一个程序执行查看器,在里面可以看见线程和堆栈等信息,TraceView是程序性能分析器
20.谈谈Android的IPC机制:

答:IPC是内部进程通信的简称,是共享"命名管道"的资源。Android中的IPC机制是为了让Activity和Service之间可以随时的进行交互,故在Android中该机制,只适用于Activity和Service之间的通信,类似于远程方法调用,类似于C/S模式的访问。通过定义AIDL接口文件来定义IPC接口。Servier端实现IPC接口,Client端调用IPC接口本地代理。
21.NDK是什么:

答:NDK是一系列工具的集合

 NDK提供了一系列的工具,帮助开发者迅速的开发C/C++的动态库,并能自动将so和java应用打成apk包

 NDK集成了交叉编译器,并提供了相应的mk文件和隔离cpu,平台等的差异,开发人员只需简单的修改mk文件就可以创建出so
22.描述一下android的系统架构:

答:android系统架构分从下往上为Linux内核层、运行库、应用程序框架层和应用程序层。

 Linux内核层:负责硬件的驱动程序、网络、电源、系统安全以及内存管理等功能。

运行库和androidruntion:运行库:即c/c++函数库部分,大多数都是开放源代码的函数库,例如webkit,该函数库负责android网页浏览器的运行;例如标准的c函数库libc、openssl、sqlite等,当然也包括支持游戏开发的2dsgl和3dopengles,在多媒体方面有mediaframework框架来支持各种影音和图形文件的播放与显示,如mpeg4、h.264、mp3、aac、amr、jpg和png等众多的多媒体文件格式。Androidruntion负责解释和执行生成的dalvik格式的字节码

应用软件架构:java应用程序开发人员主要是使用该层封装好的api进行快速开发的。

应用程序层:该层是java的应用程序层,android内置的googlemaps、email、IM、浏览器等,都处于该层,java开发人员工发的程序也处于该层,而且和内置的应用程序具有平等的地位,可以调用内置的应用程序,也可以替换内置的应用程序
23.Activity 与 Task的启动模式有哪些,它们含义具体是什么?

答:在一个activity中,有多次调用startActivity来启动另一个activity,要想只生成一个activity实例,可以设置启动模式。

 一个activity有四种启动模式:standed,signleTop,singleTask,singleInstance

 Standed:标准模式,一调用startActivity()方法就会产生一个新的实例。

 SingleTop:如果已经有一个实例位于activity栈顶,就不产生新的实例,而只是调用activity中的newInstance()方法。如果不位于栈顶,会产生一个新的实例。

 singleTask:会在一个新的task中产生这个实例,以后每次调用都会使用这个,不会去产生新的实例了。

 SingleInstance:这个和singleTask基本一样,只有一个区别:在这个模式下的activity实例所处的task中,只能有这个activity实例,不能有其他实例

24.Application类的作用:

答:API里的第一句是:

Base class for those who need to maintain global application state 

如果想在整个应用中使用全局变量,在java中一般是使用静态变量,public类型;而在android中如果使用这样的全局变量就不符合Android的框架架构,但是可以使用一种更优雅的方式就是使用Application context。 
 首先需要重写Application,主要重写里面的onCreate方法,就是创建的时候,初始化变量的值。然后在整个应用中的各个文件中就可以对该变量进行操作了。 
 启动Application时,系统会创建一个PID,即进程ID,所有的Activity就会在此进程上运行。那么我们在Application创建的时候初始化全局变量,同一个应用的所有Activity都可以取到这些全局变量的值,换句话说,我们在某一个Activity中改变了这些全局变量的值,那么在同一个应用的其他Activity中值就会改变

25.说明onSaveInstanceState() 和 onRestoreInstanceState()在什么时候被调用:

答:Activity的 onSaveInstanceState() 和 onRestoreInstanceState()并不是生命周期方法,它们不同于 onCreate()、onPause()等生命周期方法,它们并不一定会被触发。当应用遇到意外情况(如:内存不足、用户直接按Home键)由系统销毁一个Activity时,onSaveInstanceState()才会被调用。但是当用户主动去销毁一个Activity时,例如在应用中按返回键,onSaveInstanceState()就不会被调用。因为在这种情况下,用户的行为决定了不需要保存Activity的状态。通常onSaveInstanceState()只适合用于保存一些临时性的状态,而onPause()适合用于数据的持久化保存。
另外,当屏幕的方向发生了改变, Activity会被摧毁并且被重新创建,如果你想在Activity被摧毁前缓存一些数据,并且在Activity被重新创建后恢复缓存的数据。可以重写Activity的 onSaveInstanceState() 和 onRestoreInstanceState()方法。

26.android的service的生命周期?哪个方法可以多次被调用:

答:1)  与采用Context.startService()方法启动服务有关的生命周期方法
onCreate() -> onStart() -> onDestroy()
onCreate()该方法在服务被创建时调用,该方法只会被调用一次,无论调用多少次startService()或bindService()方法,服务也只被创建一次。
onStart() 只有采用Context.startService()方法启动服务时才会回调该方法。该方法在服务开始运行时被调用。多次调用startService()方法尽管不会多次创建服务,但onStart() 方法会被多次调用。
onDestroy()该方法在服务被终止时调用。
2)  与采用Context.bindService()方法启动服务有关的生命周期方法
onCreate() -> onBind() -> onUnbind() -> onDestroy()
onBind()只有采用Context.bindService()方法启动服务时才会回调该方法。该方法在调用者与服务绑定时被调用,当调用者与服务已经绑定,多次调用Context.bindService()方法并不会导致该方法被多次调用。
onUnbind()只有采用Context.bindService()方法启动服务时才会回调该方法。该方法在调用者与服务解除绑定时被调用。
如果先采用startService()方法启动服务,然后调用bindService()方法绑定到服务,再调用unbindService()方法解除绑定,最后调用bindService()方法再次绑定到服务,触发的生命周期方法如下:
onCreate() ->onStart() ->onBind() ->onUnbind()[重载后的方法需返回true] ->onRebind()

27.android的broadcast的生命周期:

答:1)  Broadcast receiver生命周期中仅有一个回调方法: 
void onReceive(Context curContext, Intent broadcastMsg) 
当接收器接收到一条broadcast消息,Android就会调用onReceiver(),并传递给它一个Intent对象,这个对象携带着那条broadcast消息。我们认为仅当执行这个方式时,Broadcast receiver是活动的;这个方法返回时,它就终止了。这就是Broadcast receiver的生命周期。 
2)  由于Broadcast receiver的生命周期很短,一个带有活动的Broadcast receiver的进程是受保护的,以避免被干掉;但是别忘了有一点,Android会在任意时刻干掉那些携带不再活动的组件的进程,所以很可能会造成这个问题。 
3)  解决上述问题的方案采用一个Service来完成这项工作,Android会认为那个进程中(Service所在的进程)仍然有在活动的组件。 
28.android view,surfaceview,glsurfaceview的区别:

答:SurfaceView是从View基类中派生出来的显示类,直接子类有GLSurfaceView和VideoView,可以看出GL和视频播放以及Camera摄像头一般均使用SurfaceView
SurfaceView和View最本质的区别在于,surfaceView是在一个新起的单独线程中可以重新绘制画面而View必须在UI的主线程中更新画面。 
那么在UI的主线程中更新画面 可能会引发问题,比如你更新画面的时间过长,那么你的主UI线程会被你正在画的函数阻塞。那么将无法响应按键,触屏等消息。 
当使用surfaceView 由于是在新的线程中更新画面所以不会阻塞你的UI主线程。但这也带来了另外一个问题,就是事件同步。比如你触屏了一下,你需要surfaceView中thread处理,一般就需要有一个event queue的设计来保存touch event,这会稍稍复杂一点,因为涉及到线程同步。 
所以基于以上,根据游戏特点,一般分成两类。 
1)被动更新画面的。比如棋类,这种用view就好了。因为画面的更新是依赖于 onTouch 来更新,可以直接使用 invalidate。 因为这种情况下,这一次Touch和下一次的Touch需要的时间比较长些,不会产生影响。 
2)主动更新。比如一个人在一直跑动。这就需要一个单独的thread不停的重绘人的状态,避免阻塞main UI thread。所以显然view不合适,需要surfaceView来控制。 

 

 

 

 

 

 

 

 

 

 

 

38. ListView如何提高其效率?

 复用convertview , 历史的view对象

异步加载数据, 分页加载数据,

使用静态的view对象 避免创建过多的view.

34. 在android中,请简述jni的调用过程。(8分)

1)安装和下载Cygwin,下载 Android NDK

  2)在ndk项目中JNI接口的设计

  3)使用C/C++实现本地方法

  4)JNI生成动态链接库.so文件

  5)将动态链接库复制到java工程,在java工程中调用,运行java工程即可

35. 简述Android应用程序结构是哪些?(7分)

Android应用程序结构是:

  Linux Kernel(Linux内核)、Libraries(系统运行库或者是c/c++核心库)、Application

  Framework(开发框架包)、Applications (核心应用程序)

36. 请继承SQLiteOpenHelper实现:(10分) 

1).创建一个版本为1的“diaryOpenHelper.db”的数据库,

  2).同时创建一个 “diary” 表(包含一个_id主键并自增长,topic字符型100

  长度, content字符型1000长度)

  3).在数据库版本变化时请删除diary表,并重新创建出diary表。

  publicclass DBHelper extends SQLiteOpenHelper{

  public final static String DATABASENAME ="diaryOpenHelper.db";

  public final static int DATABASEVERSION =1;

  //创建数据库

  public DBHelper(Context context,Stringname,CursorFactory factory,int version)

  {

  super(context, name, factory,version);

  }

  //创建表等机构性文件

  public void onCreate(SQLiteDatabase db)

  {

  String sql ="create tablediary"+

  "("+

  "_idinteger primary key autoincrement,"+

  "topicvarchar(100),"+

  "contentvarchar(1000)"+

  ")";

  db.execSQL(sql);

  }

  //若数据库版本有更新,则调用此方法

  public void onUpgrade(SQLiteDatabasedb,int oldVersion,int newVersion)

  {

  String sql = "drop table ifexists diary";

  db.execSQL(sql);

  this.onCreate(db);

  }

  }

  37. 页面上现有ProgressBar控件progressBar,请用书写线程以10秒的的时间完成其进度显示工作。(10分)答案

  publicclass ProgressBarStu extends Activity {

  private ProgressBar progressBar = null;

  protected void onCreate(BundlesavedInstanceState) {

  super.onCreate(savedInstanceState);

  setContentView(R.layout.progressbar);

  //从这到下是关键

  progressBar = (ProgressBar)findViewById(R.id.progressBar);

  Thread thread = new Thread(newRunnable() {

  @Override

  public void run() {

  int progressBarMax =progressBar.getMax();

  try {

  while(progressBarMax!=progressBar.getProgress())

  {

  intstepProgress = progressBarMax/10;

  intcurrentprogress = progressBar.getProgress();

  progressBar.setProgress(currentprogress+stepProgress);

  Thread.sleep(1000);

  }

  } catch(InterruptedException e) {

  // TODO Auto-generatedcatch block

  e.printStackTrace();

  }

  }

  });

  thread.start();

  //关键结束

  }

  }

38. 请描述下Activity的生命周期。 

必调用的三个方法:onCreate() --> onStart() --> onResume(),用AAA表示

  (1)父Activity启动子Activity,子Actvity退出,父Activity调用顺序如下

  AAA --> onFreeze() --> onPause() --> onStop() --> onRestart()--> onStart(),onResume() …

  (2)用户点击Home,Actvity调用顺序如下

  AAA --> onFreeze() --> onPause() --> onStop() -- Maybe -->onDestroy() – Maybe

  (3)调用finish(), Activity调用顺序如下

  AAA --> onPause() --> onStop() --> onDestroy()

  (4)在Activity上显示dialog,Activity调用顺序如下

  AAA

  (5)在父Activity上显示透明的或非全屏的activity,Activity调用顺序如下

  AAA --> onFreeze() --> onPause()

  (6)设备进入睡眠状态,Activity调用顺序如下

  AAA --> onFreeze() --> onPause()

39. 如果后台的Activity由于某原因被系统回收了,如何在被系统回收之前保存当前状态? 

     onSaveInstanceState()当你的程序中某一个Activity A在运行时,主动或被动地运行另一个新的Activity B,这个时候A会执行onSaveInstanceState()。B完成以后又会来找A,这个时候就有两种情况:一是A被回收,二是A没有被回收,被回收的A就要重新调用onCreate()方法,不同于直接启动的是这回onCreate()里是带上了参数savedInstanceState;而没被收回的就直接执行onResume(),跳过onCreate()了。

 

1.你的Activity被系统回收了怎么办?

  除了在栈顶的activity,其他的activity都有可能在内存不足的时候被系统回收,一个activity越处于栈底,被回收的可能性越大.protected void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); outState.putLong("id", 1234567890);}public void onCreate(Bundle savedInstanceState) {//判断 savedInstanceState是不是空.//如果不为空就取出来        super.onCreate(savedInstanceState);}

1.简要写一个完全退出应用程序的方法。

自定义一个Actiivty 栈,道理同上,不过利用一个单例模式的Activity栈来管理所有Activity。并提供退出所有Activity的方法。代码如下:

   public class ScreenManager {
 private static Stack<Activity> activityStack;
 private static ScreenManager instance;
 private  ScreenManager(){
 }
 public static ScreenManager getScreenManager(){
  if(instance==null){
   instance=new ScreenManager();
  }
  return instance;
 }
//退出栈顶Activity
 public void popActivity(Activity activity){
  if(activity!=null){
   activity.finish();
   activityStack.remove(activity);
   activity=null;
  }
 }

//获得当前栈顶Activity
 public Activity currentActivity(){
  Activity activity=activityStack.lastElement();
  return activity;
 }

//将当前Activity推入栈中
 public void pushActivity(Activity activity){
  if(activityStack==null){
   activityStack=new Stack<Activity>();
  }
  activityStack.add(activity);
 }
 //退出栈中所有Activity
 public void popAllActivityExceptOne(Class cls){
  while(true){
   Activity activity=currentActivity();
   if(activity==null){
    break;
   }
   if(activity.getClass().equals(cls) ){
    break;
   }
   popActivity(activity);
  }
 }
}

2. Activity有几种启动方式。简要描述有什么区别。

  standard(默认), singleTop, singleTask和 singleInstance

3.Android都有哪些XML解析器,各自的优缺点是什么?

  Pull   SAX   dom  dom4j

4.注册广播有几种方式,这些方式有何优缺点?

  首先写一个类要继承BroadcastReceiver 第一种:在清单文件中声明,添加 

<receive android:name=".IncomingSMSReceiver " > <intent-filter> 

   <action android:name="android.provider.Telephony.SMS_RECEIVED") <intent-filter> <receiver> 

第二种使用代码进行注册如: IntentFilter filter =  new 

IntentFilter("android.provider.Telephony.SMS_RECEIVED"); IncomingSMSReceiver receiver = new IncomgSMSReceiver(); registerReceiver(receiver.filter); 两种注册类型的区别是: 

1)第一种不是常驻型广播,也就是说广播跟随程序的生命周期。 

2)第二种是常驻型,也就是说当应用程序关闭后,如果有信息广播来,程序也会被系统调用自动运行。

5.谈谈你对AIDL的理解。

它是一种android内部进程通信接口的描述语言,通过它我们可以定义进程间的通信接口
icp:interprocess communication :内部进程通信

6.曾经使用或是了解过fragment吗,简要谈谈你的理解。

 Fragment是activity的界面中的一部分或一种行为. 可以把Fragment认为模块化的一段activity,它具有自己的生命周期,接收它自己的事件,并可以在activity运行时被添加或删除。 

Fragment不能独立存在,它必须嵌入到activity中,而且Fragment的生命周期直接受所在的activity的影响。当向activity中添加一个Fragment时,它须置于ViewGroup控件中,并且需定义Fragment自己的界面。

Android笔试题

一. 选择题(30题,每个15分,共45分)

1. java.io包中定义了多个流类型来实现输入和输出功能,可以从不同的角度对其进行分类,按功能分为:(C),如果为读取的内容进行后台处理后在输出,需要使用下列哪种流?(A)

A、 输入流和输出流

B、 字节流和字符流

C、 节点流和处理流

D、 File stream

E、 Pipe stream

F、 Random stream

G、 Filter stream

2.下列代码的执行结果是:(B)

public class Test3{

public static void main(String args[]){

System.out.print(100%3);

System.out.print(“,”);

System.out.print(100%3.0);

}

}

A、.1 , 1

B、1 , 1.0

C、1.0 ,1

D、1.0 ,1.0

3、在继承中,关于构造方法的说明,下列说法错误的是(D)

A、子类无条件的继承父类中的无参构造方法

B、子类可以引用父类中的有参构造方法,使用super关键字

C、如果子类没有构造方法,则父类无参构造方法作为自己的构造方法

D、如果子类有无参的构造方法,而父类的无参构造方法则被覆盖

4、以下的程序的运行结果为(D)

Public class IfTest{

Public static void main(String args[]){

int x=3;

int y=1;

if(x==y)

System.out.println(“Not equal”);

Else

System.out.println(“Equal”);

}

}

A、 Not equal 

B、 Equal

C、 无输出

D、 编译错误

5、Java语言中字符串“学java”所占的内存空间是(C)

A、6个字节

B、7个字节

C、10个字节

D、11个字节

6、关于下列程序段的输出结果,说法正确的是(A)

public class MyClass{

static int i;

public static void main(String args[]){

System.out.println(i);

}

}

A、 有错误,变量i没有初始化

B、 Null

C、 1

D、 0

7、下列那些语句关于内存回收的说明是正确的(B)

A、程序员必须穿件一个内存来释放内存

B、内存回收程序负责释放无用内存

C、内存回收程序允许程序员直接释放内存

D、内存回收程序可以在指定的时间释放内存对象

8、下面异常是属于Runtime Exception的是(B C)?(多选)

A、ArithmeticException

B、IllegalArgumentException

C、NullPointerException

D、BufferUnderflowException

9、Math.round(11.5)等于多少?Math.round(-11.5)等于多少(C)

A、11,-11

B、11,-12

C、12,-11

D、12,-12

10、下列程序段输出的结果是:(B)

Void complicatedexpression_r(){

int x=20,y=30;

boolean b;

b=x>50&&y>60||x>50&&y<-60||x<-50&&y>60||x<-50&&y<-60;

System.out.println(b)

}

A、 true

B、 false

C、 1

D、 0

11、activity对一些资源以及状态的操作保存,最好是保存在生命周期的哪个函数中进行(D)

A、onPause()

B、onCreate()

C、onResume()

D、onStart()

12、Intent传递数据时,下列数据类型哪些可以被传递(A D)(多选)

A、Serializable

B、charsequence

C、Parcelable

D、Bundle

13、android中下列属于Intent的作用的是(C)

A、实现应用程序间的数据共享

B、是一段长的声明周期,没有用户界面的程序,可以保持应用在后再运行,而不会因为切换页面而消失

C、可以实现界面间的切换,可以包含动作和动作数据,连接四大组件的纽带

D、处理一个应用程序的整体性工作

Android 面试题(1)

1.    请描述下Activity的生命周期

详细介绍一下这几个方法中系统在做什么以及我们应该做什么:

  onCreate:   在这里创建界面 ,做一些数据的初始化工作

  onStart:    到这一步变成用户可见不可交互 的

  onResume:   变成和用户可交互 的,(在activity 栈系统通过栈的方式管理这些个      
                      Activity的最上面,运行完弹出栈,则回到上一个Activity)

  onPause:     到这一步是可见但不可交互 的,系统会停止动画 等消耗CPU 的事情
                    从上文的描述已经知道,应该在这里保存你的一些数据,因为这个时候
                    你的程序的优先级降低,有可能被系统收回。在这里保存的数据,应该在

                   onResume里读出来,注意:这个方法里做的事情时间要短,因为下一
                    个activity不会等到这个方法完成才启动

  onstop:     变得不可见 ,被下一个activity覆盖了

  onDestroy: 这是activity被干掉前最后一个被调用方法了,可能是外面类调用finish方
                     法或者是系统为了节省空间将它暂时性的干掉,可以用isFinishing()来判
                     断它,如果你有一个Progress Dialog在线程中转动,请在onDestroy里
                     把他cancel掉,不然等线程结束的时候,调用Dialog的cancel方法会抛
                     异常的。

            
onPause,onstop, onDestroy,三种状态 下 activity都有可能被系统干掉
为了保证程序的正确性,你要在onPause()里写上持久层操作的代码,将用户编辑的内容都保存到存储介质上(一般都是数据库)。实际工作中因为生命周期的变化而带来的问题也很多,比如你的应用程序起了新的线程在跑,这时候中断了,你还要去维护那个线程,是暂停还是杀掉还是数据回滚,是吧?因为Activity可能被杀掉,所以线程中使用的变量和一些界面元素就千万要注意了,一般我都是采用Android的消息机制 [Handler,Message]来处理多线程和界面交互的问题。这个我后面会讲一些,最近因为这些东西头已经很大了,等我理清思绪再跟大家分享。


2.    如果后台的Activity由于某原因被系统回收了,如何在被系统回收之前保存当前状态?
当你的程序中某一个Activity A 在运行时中,主动或被动地运行另一个新的Activity B

这个时候A会执行

Java代码

1 public 

2 void onSaveInstanceState(Bundle outState) {    

3 super.onSaveInstanceState(outState); 

4 outState.putLong("id", 1234567890);    

5 } 

7 public void onSaveInstanceState(Bundle outState) {    super.onSaveInstanceState(outState);    outState.putLong("id", 1234567890);} 


B 完成以后又会来找A, 这个时候就有两种情况,一种是A被回收,一种是没有被回收,被回
收的A就要重新调用onCreate()方法,不同于直接启动的是这回onCreate()里是带上参数
savedInstanceState,没被收回的就还是onResume就好了。

savedInstanceState是一个Bundle对象,你基本上可以把他理解为系统帮你维护的一个Map对象。在onCreate()里你可能会用到它,如果正常启动onCreate就不会有它,所以用的时候要判断一下是否为空。

Java代码


if(savedInstanceState != null){  
     long id = savedInstanceState.getLong("id");  
}  

if(savedInstanceState != null){     long id = savedInstanceState.getLong("id");}


就像官方的Notepad教程里的情况,你正在编辑某一个note,突然被中断,那么就把这个note的id记住,再起来的时候就可以根据这个id去把那个note取出来,程序就完整一些。这也是看你的应用需不需要保存什么,比如你的界面就是读取一个列表,那就不需要特殊记住什么,哦,没准你需要记住滚动条的位置...

3.    如何将一个Activity设置成窗口的样式

简单你只需要设置 一下Activity的主题就可以了在AndroidManifest.xml 中定义 Activity的
地方一句话: 


Xml代码

9 android :theme="@android:style/Theme.Dialog" 


这就使你的应用程序变成对话框的形式弹出来了,或者


Xml代码

 android:theme="@android:style/Theme.Translucent" 

就变成半透明的,[友情提示-.-]类似的这种activity的属性可以在android.R.styleable 类的AndroidManifestActivity 方法中看到,AndroidManifest.xml中所有元素的属性的介绍都可以参考这个类android.R.styleable

上面说的是属性名称,具体有什么值是在android.R.style中可以看到,比如这个"@android:style/Theme.Dialog" 就对应于android.R.style.Theme_Dialog ,('_'换成'.' <--注意:这个是文章内容不是笑脸)就可以用在描述文件中了,找找类定义和描述文件中的对应关系就都明白了。

4.    如何退出Activity
对于单一Activity的应用来说,退出很简单,直接finish()即可。
当然,也可以用killProcess()和System.exit()这样的方法。
现提供几个方法,供参考:
1、抛异常强制退出:
该方法通过抛异常,使程序Force Close。
验证可以,但是,需要解决的问题是,如何使程序结束掉,而不弹出Force Close的窗口。

2、记录打开的Activity:
每打开一个Activity,就记录下来。在需要退出时,关闭每一个Activity即可。

3、发送特定广播:
在需要结束应用时,发送一个特定的广播,每个Activity收到广播后,关闭即可。

4、递归退出
在打开新的Activity时使用startActivityForResult,然后自己加标志,在onActivityResult中处理,递归关闭。
除了第一个,都是想办法把每一个Activity都结束掉,间接达到目的。
但是这样做同样不完美。
你会发现,如果自己的应用程序对每一个Activity都设置了nosensor,在两个Activity结束的间隙,sensor可能有效了。
但至少,我们的目的达到了,而且没有影响用户使用。
为了编程方便,最好定义一个Activity基类,处理这些共通问题。



5.请介绍下Android中常用的五种布局
Android布局是应用界面开发的重要一环,在Android中,共有五种布局方式,分别是:FrameLayout(框架布
局),LinearLayout 
(线性布局),AbsoluteLayout(绝对布局),RelativeLayout(相对布局),TableLayout(表格布局)。
  
    一、FrameLayout
    这个布局可以看成是墙脚堆东西,有一个四方的矩形的左上角墙脚,我们放了第一个东西,要再放一个,那就在放在原来放的位置的上面,这样依次的放,会盖住原来的东西。这个布局比较简单,也只能放一点比较简单的东西。

    二、LinearLayout
线性布局,这个东西,从外框上可以理解为一个div,他首先是一个一个从上往下罗列在屏幕上。每一个LinearLayout里面又可分为垂直布局
(android:orientation="vertical")和水平布局(android:orientation="horizontal"
)。当垂直布局时,每一行就只有一个元素,多个元素依次垂直往下;水平布局时,只有一行,每一个元素依次向右排列。
    linearLayout中有一个重要的属性 android:layout_weight="1",这个weight在垂直布局时,代表行距;水平的时候代表列宽;weight值越大就越大。

    三、AbsoluteLayout
 绝对布局犹如div指定了absolute属性,用X,Y坐标来指定元素的位置android:layout_x="20px"
android:layout_y="12px" 这种布局方式也比较简单,但是在垂直随便切换时,往往会出问题,而且多个元素的时候,计算比较麻烦。

   

    四、RelativeLayout

    相对布局可以理解为某一个元素为参照物,来定位的布局方式。主要属性有:

   

    相对于某一个元素

    android:layout_below="@id/aaa" 该元素在 id为aaa的下面
    android:layout_toLeftOf="@id/bbb" 改元素的左边是bbb

    相对于父元素的地方

    android:layout_alignParentLeft="true"  在父元素左对齐

    android:layout_alignParentRight="true" 在父元素右对齐

    还可以指定边距等,具体详见API

   
    五。TableLayout
    表格布局类似Html里面的Table。每一个TableLayout里面有表格行TableRow,TableRow里面可以具体定义每一个元素,设定他的对齐方式 android:gravity="" 。

    每一个布局都有自己适合的方式,另外,这五个布局元素可以相互嵌套应用,做出美观的界面。


6.    请介绍下Android的数据存储方式
Android 提供了5种方式存储数据:

--使用SharedPreferences存储数据;
--文件存储数据;
--SQLite数据库存储数据;
--使用ContentProvider存储数据;
--网络存储数据;

先 说下,Preference,File, DataBase这三种方式分别对应的目录是/data/data/Package Name/Shared_Pref, /data/data/Package Name/files, /data/data/Package Name/database 。

在Android中通常使用File存储方式是用 Context.openFileOutput(String fileName, int mode)和Context.openFileInput(String fileName)。
Context.openFileOutput(String fileName, int mode)生成的文件自动存储在/data/data/Package Name/files目录下,其全路径是/data/data/Package Name/files/fileName 。注意下,这里的参数fileName不可以包含路径分割符(如"/")。
通常来说,这种方式生成的文件只能在这个apk内访问。但这个结论是指使用Context.openFileInput(String fileName)的方式。使用这种方式,每个apk只可以访问自己的/data/data/Package Name/files目录下的文件,原因很简单,参数fileName中不可以包含路径分割符,Android会自动在/data/data /Package Name/files目录下寻找文件名为fileName的文件。

一:使用SharedPreferences存储数据

首先说明SharedPreferences存储方式,它是 Android提供的用来存储一些简单配置信息的一种机制,例如:登录用户的用户名与密码。其采用了Map数据结构来存储数据,以键值的方式存储,可以简单的读取与写入,具体实例如下:
void ReadSharedPreferences(){
String strName,strPassword;
SharedPreferences   user = getSharedPreferences(“user_info”,0);
strName = user.getString(“NAME”,””);
strPassword = user getString(“PASSWORD”,””);
}
void WriteSharedPreferences(String strName,String strPassword){
SharedPreferences   user = getSharedPreferences(“user_info”,0);
uer.edit();
user.putString(“NAME”, strName);
user.putString(“PASSWORD” ,strPassword);
user.commit();
}
数据读取与写入的方法都非常简单,只是在写入的时候有些区别:先调用edit()使其处于编辑状态,然后才能修改数据,最后使用commit()提交修改的数据。实际上SharedPreferences是采用了XML格式将数据存储到设备中,在DDMS中的File Explorer中的/data/data/<package name>/shares_prefs下。以上面的数据存储结果为例,打开后可以看到一个user_info.xml的文件,打开后可以看到:
<?xml version=”1.0″ encoding=”UTF-8″?>
<map>
<string name=”NAME”>moandroid</string>
<string name=” PASSWORD”>SharedPreferences</string>
</map>
使用SharedPreferences是有些限制的:只能在同一个包内使用,不能在不同的包之间使用。

二:文件存储数据


文件存储方式是一种较常用的方法,在Android中读取/写入文件的方法,与 Java中实现I/O的程序是完全一样的,提供了openFileInput()和openFileOutput()方法来读取设备上的文件。 FilterInputStream, FilterOutputStream等可以到Java io package说明中去详细学习,不再此详细说明,具体实例如下:
String fn = “moandroid.log”;
FileInputStream fis = openFileInput(fn);
FileOutputStream fos = openFileOutput(fn,Context.MODE_PRIVATE);
除此之外,Android还提供了其他函数来操作文件,详细说明请阅读Android SDK。

三:网络存储数据


网络存储方式,需要与Android 网络数据包打交道,关于Android 网络数据包的详细说明,请阅读Android SDK引用了Java SDK的哪些package?。

四:ContentProvider

1、ContentProvider简介


当应用继承ContentProvider类,并重写该类用于提供数据和存储数据的方法,就可以向其他应用共享其数据。虽然使用其他方法也可以对外共享数据,但数据访问方式会因数据存储的方式而不同,如:采用文件方式对外共享数据,需要进行文件操作读写数据;采用sharedpreferences共享数据,需要使用sharedpreferences API读写数据。而使用ContentProvider共享数据的好处是统一了数据访问方式。?

2、Uri类简介


Uri代表了要操作的数据,Uri主要包含了两部分信息:1.需要操作的ContentProvider ,2.对ContentProvider中的什么数据进行操作,一个Uri由以下几部分组成:
1.scheme:ContentProvider(内容提供者)的scheme已经由Android所规定为:content://。


2.主机名(或Authority):用于唯一标识这个ContentProvider,外部调用者可以根据这个标识来找到它。


3.路径(path):可以用来表示我们要操作的数据,路径的构建应根据业务而定,如下:
? 要操作contact表中id为10的记录,可以构建这样的路径:/contact/10
? 要操作contact表中id为10的记录的name字段, contact/10/name
? 要操作contact表中的所有记录,可以构建这样的路径:/contact?
要操作的数据不一定来自数据库,也可以是文件等他存储方式,如下:
要操作xml文件中contact节点下的name节点,可以构建这样的路径:/contact/name
如果要把一个字符串转换成Uri,可以使用Uri类中的parse()方法,如下:
Uri uri = Uri.parse("content://com.changcheng.provider.contactprovider/contact")
3、UriMatcher、ContentUrist和ContentResolver简介

因为Uri代表了要操作的数据,所以我们很经常需要解析Uri,并从 Uri中获取数据。Android系统提供了两个用于操作Uri的工具类,分别为UriMatcher 和ContentUris 。掌握它们的使用,会便于我们的开发工作。
? UriMatcher:用于匹配Uri,它的用法如下:


1.首先把你需要匹配Uri路径全部给注册上,如下:
//常量UriMatcher.NO_MATCH表示不匹配任何路径的返回码(-1)。
UriMatcher uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
//如果match()方法匹配content://com.changcheng.sqlite.provider.contactprovider /contact路径,返回匹配码为1
uriMatcher.addURI(“com.changcheng.sqlite.provider.contactprovider”, “contact”, 1);//添加需要匹配uri,如果匹配就会返回匹配码
//如果match()方法匹配 content://com.changcheng.sqlite.provider.contactprovider/contact/230路径,返回匹配码为2
uriMatcher.addURI(“com.changcheng.sqlite.provider.contactprovider”, “contact/#”, 2);//#号为通配符

2.注册完需要匹配的Uri后,就可以使用uriMatcher.match(uri)方法对输入的Uri进行匹配,如果匹配就返回匹配码,匹配码是调用 addURI()方法传入的第三个参数,假设匹配 content://com.changcheng.sqlite.provider.contactprovider/contact路径,返回的匹配码为1。
?
ContentUris:用于获取Uri路径后面的ID部分,它有两个比较实用的方法:
? withAppendedId(uri, id)用于为路径加上ID部分
? parseId(uri)方法用于从路径中获取ID部分
? ContentResolver:当外部应用需要对ContentProvider中的数据进行添加、删除、修改和查询操作时,可以使用 ContentResolver 类来完成,要获取ContentResolver 对象,可以使用Activity提供的getContentResolver()方法。 ContentResolver使用insert、delete、update、query方法,来操作数据。

五:总结说明


以上5中存储方式,在以后的开发过程中,根据设计目标、性能需求、空间需求等找到合适的数据存储方式。Android 中的数据存储都是私有的,其他应用程序都是无法访问的,除非通过ContentResolver获取其他程序共享的数据。采用文件方式对外共享数据,需要进行文件操作读写数据;采用sharedpreferences共享数据,需要使用sharedpreferences API读写数据。而使用ContentProvider共享数据的好处是统一了数据访问方式。

8.如何启用Service,如何停用ServiceAndroid中的服务和windows中的服务是类似的东西,服务一般没有用户操作界面,它运行于系统中不容易被用户发觉,可以使用它开发如监控之类的程序。服务的开发比较简单,如下:

第一步:继承Service类

public class SMSService extends Service {

}

第二步:在AndroidManifest.xml文件中的<application>节点里对服务进行配置:

<service android:name=".SMSService" />

服务不能自己运行,需要通过调用Context.startService()或Context.bindService()方法启动服务。这两个方法都可以启动Service,但是它们的使用场合有所不同。使用startService()方法启用服务,调用者与服务之间没有关连,即使调用者退出了,服务仍然运行。使用bindService()方法启用服务,调用者与服务绑定在了一起,调用者一旦退出,服务也就终止,大有“不求同时生,必须同时死”的特点。

如果打算采用Context.startService()方法启动服务,在服务未被创建时,系统会先调用服务的onCreate()方法,接着调用onStart()方法。如果调用startService()方法前服务已经被创建,多次调用startService()方法并不会导致多次创建服务,但会导致多次调用onStart()方法。采用startService()方法启动的服务,只能调用Context.stopService()方法结束服务,服务结束时会调用onDestroy()方法。

如果打算采用Context.bindService()方法启动服务,在服务未被创建时,系统会先调用服务的onCreate()方法,接着调用onBind()方法。这个时候调用者和服务绑定在一起,调用者退出了,系统就会先调用服务的onUnbind()方法,接着调用onDestroy()方法。如果调用bindService()方法前服务已经被绑定,多次调用bindService()方法并不会导致多次创建服务及绑定(也就是说onCreate()和onBind()方法并不会被多次调用)。如果调用者希望与正在绑定的服务解除绑定,可以调用unbindService()方法,调用该方法也会导致系统调用服务的onUnbind()-->onDestroy()方法。

服务常用生命周期回调方法如下:onCreate() 该方法在服务被创建时调用,该方法只会被调用一次,无论调用多少次startService()或bindService()方法,服务也只被创建一次。

onDestroy()该方法在服务被终止时调用。

与采用Context.startService()方法启动服务有关的生命周期方法

onStart() 只有采用Context.startService()方法启动服务时才会回调该方法。该方法在服务开始运行时被调用。多次调用startService()方法尽管不会多次创建服务,但onStart() 方法会被多次调用。

与采用Context.bindService()方法启动服务有关的生命周期方法

onBind()只有采用Context.bindService()方法启动服务时才会回调该方法。该方法在调用者与服务绑定时被调用,当调用者与服务已经绑定,多次调用Context.bindService()方法并不会导致该方法被多次调用。

onUnbind()只有采用Context.bindService()方法启动服务时才会回调该方法。该方法在调用者与服务解除绑定时被调用

采用Context.startService()方法启动服务的代码如下:

public class HelloActivity extends Activity {

   @Override

   public void onCreate(Bundle savedInstanceState) {

       ......

       Button button =(Button) this.findViewById(R.id.button);

       button.setOnClickListener(new View.OnClickListener(){

      public void onClick(View v) {

             Intent intent = new Intent(HelloActivity.this, SMSService.class);

             startService(intent);

      }});       

   }

}

采用Context. bindService()方法启动服务的代码如下:

public class HelloActivity extends Activity {

    ServiceConnection conn = new ServiceConnection() {

            public void onServiceConnected(ComponentName name, IBinder service) {

         }

         public void onServiceDisconnected(ComponentName name) {

         }

    };

   @Override public void onCreate(Bundle savedInstanceState) { 

       Button button =(Button) this.findViewById(R.id.button);

       button.setOnClickListener(new View.OnClickListener(){

             public void onClick(View v) {

                Intent intent = new Intent(HelloActivity.this, SMSService.class);

                 bindService(intent, conn, Context.BIND_AUTO_CREATE);

                //unbindService(conn);//解除绑定

        }});       

   }

}


 

==架构编===============================================================

说说mvc模式的原理,它在android中的运用

mvc是model,view,controller的缩写,mvc包含三个部分:

  l模型(model)对象:是应用程序的主体部分,所有的业务逻辑都应该写在该层。

  2视图(view)对象:是应用程序中负责生成用户界面的部分。也是在整个mvc架构中用户唯一可以看到的一层,接收用户的输入,显示处理结果。

  3控制器(control)对象:是根据用户的输入,控制用户界面数据显示及更新model对象状态的部分,控制器更重要的一种导航功能,用户触发的相关事件,由control层交给model层处理;待model层处理完结果后,再由control层交还给view层显示处理结果。

Mvc的优点:
1.耦合度低
2.重用性高
3.可维护性高

4.有利于二次卡法

5.部署快
6.有利软件工程化管理


Mvc的缺点:
1.不适合小型,中等规模的应用程序
2.增加系统结构和实现的复杂性
3.视图与控制器间的过于紧密的连接
4.视图对模型数据的低效率访问
5.一般高级的界面工具或构造器不支持模式

  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值