1. 程式人生 > >Android面試題2

Android面試題2

20.圖片的非同步載入的方法?

1.利用軟引用來快取圖片Bitmap,用圖片的URL作為快取查詢的Key 
2.設兩級快取,一級是SoftReference,二級是本地SD卡; 
3.如果兩級快取都沒取到圖片,則從伺服器獲取,並加入快取; 
4.載入完後通過回撥介面通知UI更新; 

瀑布流實現方式?

1)自定義scrollView,動態程式碼新增LinearLayout及ImageView

      a.自定義scrollView,並且使用監聽器模式,對其滾動到最頂部、及最底部進行監聽操作。

      b.在Activity裡對scrollView的橫向的LinearLayout動態新增列數,每一列是一個豎向的linearLayout.

      c.根據列數以及list.size()對每一列的linearLayout新增ImageView.

      d.根據監聽器對其滾動到頂部(不做操作)、滾到最底部(載入更多資料)、正在滾動進行操作(滾動超過兩屏,回收兩屏之前圖片回收及回滾到之前螢幕圖片過載)。

把一張特別大的圖片,分成幾十張小的圖片,在最短的時間內給處理?

http://www.linuxidc.com/Linux/2012-11/73939p2.htm

方法1:如果你將return-data設定為“true”,你將會獲得一個與內部資料關聯的Action,並且bitmap以此方式返回:(Bitmap)extras.getParcelable("data")。注意:如果你最終要獲取的圖片非常大,那麼此方法會給你帶來麻煩,所以你要控制outputX和outputY保持在較小的尺寸。鑑於此原因,在我的程式碼中沒有使用此方法((Bitmap)extras.getParcelable("data"))。


方法2: 如果你將return-data設定為“false”,那麼在onActivityResult的Intent資料中你將不會接收到任何Bitmap,相反,你需要將MediaStore.EXTRA_OUTPUT關聯到一個Uri,此Uri是用來存放Bitmap的。但是還有一些條件,首先你需要有一個短暫的與此Uri相關聯的檔案地址,當然這不是個大問題(除非是那些沒有sdcard的裝置)。

 

Android dvm的程序和Linux的程序, 應用程式的程序是否為同一個概念?

DVM指dalivk的虛擬機器。每一個Android應用程式都在它自己的程序中執行,都擁有一個獨立的Dalvik虛擬機器例項。而每一個DVM程序都是在Linux系統中的一個程序,所以可以認為是同一個概念。 

Dalvik和Java執行環境的區別  [
1:Dalvik主要是完成物件生命週期管理,堆疊管理,執行緒管理,安全和異常管理,以及垃圾回收等等重要功能。
2:Dalvik負責程序隔離和執行緒管理,每一個Android應用在底層都會對應一個獨立的Dalvik虛擬機器例項,其程式碼在虛擬機器的解釋下得以執行。   
3:不同於Java虛擬機器執行java位元組碼,Dalvik虛擬機器執行的是其專有的檔案格式Dex 4:dex檔案格式可以減少整體檔案尺寸,提高I/o操作的類查詢速度。   
5:odex是為了在執行過程中進一步提高效能,對dex檔案的進一步優化。   
6:所有的Android應用的執行緒都對應一個Linux執行緒,虛擬機器因而可以更多的依賴作業系統執行緒排程管理機制 
7:有一個特殊的虛擬機器程序Zygote,他是虛擬機器例項的孵化器。它在系統啟動的時候就會產生,它會完成虛擬機器的初始化,庫的載入,預製類庫和初始化的操作。如果系統需要一個新的虛擬機器例項,它會迅速複製自身,以最快的資料提供給系統。對於一些只讀的系統庫,所有虛擬機器例項都和Zygote共享一塊記憶體區域。

  1. 嵌入式作業系統記憶體管理有哪幾種,各有何特性 ?

 1、虛擬記憶體管理機制: 有一些嵌入式處理器提供了MMU,在MMU具備記憶體地址對映和定址功能,它使作業系統的記憶體管理更加方便。如果存在MMU ,作業系統會使用它完成從虛擬地址到實體地址的轉換, 所有的應用程式只需要使用虛擬地址定址資料。 這種使用虛擬地址定址整個系統的主存和輔存的方式在現代作業系統中被稱為虛擬記憶體。MMU 便是實現虛擬記憶體的必要條件。 虛擬記憶體的管理方法使系統既可以執行體積比實體記憶體還要大的應用程式,也可以實現“按需調頁”策略,既滿足了程式的執行速度,又節約了實體記憶體空間。 在L inux系統中,虛擬記憶體機制的實現實現為我們提供了一個典型的例子:在不同的體系結構下, 使用了三級或者兩級頁式管理,利用MMU 完成從虛擬地址到實體地址之間的轉換。基於虛擬記憶體管理的記憶體最大好處是:由於不同程序有自己單獨的程序空間,十分有效的提高了系統可靠性和安全性。 2、非虛擬記憶體管理機制: 在實時性要求比較高的情況下,很多嵌入式系統並不需要虛擬記憶體機制:因為虛擬記憶體機制會導致不確定性的 I/O阻塞時間, 使得程式執行時間不可預期,這是實時嵌入式系統的致命缺陷;另外,從嵌入式處理器的成本考慮,大多采用不裝配MMU 的嵌入式微處理器。所以大多嵌入式系統採用的是實儲存器管理策略。因而對於記憶體的訪問是直接的,它對地址的訪問不需要經過MMU,而是直接送到地址線上輸出,所有程式中訪問的地址都是實際的實體地址;而且,大多數嵌入式作業系統對記憶體空間沒有保護,各個程序實際上共享一個執行空間。一個程序在執行前,系統必須為它分配足夠的連續地址空間,然後全部載入主儲存器的連續空間。

 

  1. 什麼是嵌入式實時作業系統, Android 作業系統屬於實時作業系統嗎?

嵌入式實時作業系統是指當外界事件或資料產生時,能夠接受並以足夠快的速度予以處理,其處理的結果又能在規定的時間之內來控制生產過程或對處理系統作出快速響應,並控制所有實時任務協調一致執行的嵌入式作業系統
    嵌入式作業系統主要用於工業控制、軍事裝置、航空航天等領域對系統的響應時間有苛刻的要求,這就需要使用實時系統。又可分為軟實時和硬實時兩種,而 android 是基於 linux 核心的,因此屬於軟實時。

26.一條最長的簡訊息約佔多少byte? 

一條最長的簡訊息約佔140byte

 

  1. android中的動畫有哪幾類,它們的特點和區別是什麼?

答:Android中動畫可以分為兩大類:幀動畫、補間動畫

1)補間動畫:(你定義一個開始和結束,中間的部分由程式運算得到。就是對場景裡的物件不斷的進行影象變化來產生動畫效果(旋轉、平移、放縮和漸變))AlphaAnimation(漸變型動畫)、scaleAnimation(縮放型動畫)、 TranslateAnimation(平移型動畫)、 RotateAnimation(旋轉型動畫)、

2)逐幀動畫:Frame(把一連串的圖片進行系列化連續播放,如同放電影的效果),它是通過播放一張一張圖片來達到動畫的效果;

28.handler機制的原理,looper通過什麼方法開始的?

一個Handler允許你傳送和處理Message和Runable物件,每個執行緒都有自己的Looper,每個Looper中封裝著MessageQueue。Looper負責不斷的從自己的訊息佇列裡取出隊頭的任務或訊息執行。每個handler也和執行緒關聯,Handler負責把Message和Runable物件傳遞給MessageQueue(用到post ,sendMessage等方法),而且在這些物件離開MessageQueue時,Handler負責執行他們(用到handleMessage方法)。

其中Message類就是定義了一個資訊,這個資訊中包含一個描述符和任意的資料物件,這個資訊被用來傳遞給Handler.Message物件提供額外的兩個int域和一個Object域。

預設情況下一個執行緒是不存在訊息迴圈(message loop)的,需要呼叫Looper.prepare()來給執行緒建立一個訊息迴圈,呼叫Looper.loop()來使訊息迴圈起作用,從訊息佇列裡取訊息,處理訊息。呼叫Looper.loop()之後迴圈已經開始,下一個由handler發的message將會被這個handler的handleMessage方法處理,這是一個----迴圈。

Looper從MessageQueue中取出Message之後,交由Handler的handleMessage進行處理。處理完成後,呼叫Message.recycle()將其放入Message Pool中。

29.說說mvc模式的原理,在android中的運用?

答:mvc是model,view,controller的縮寫,mvc包含三個部分:
  模型(model)物件:是應用程式的主體部分,所有的業務邏輯都應該寫在該層。
  檢視(view)物件:是應用程式中負責生成使用者介面的部分。也是在整個mvc架構中使用者唯一可以看到的一層,接收使用者的輸入,顯示處理結果。
  控制器(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裡面處理,當然對業務計算等操作也是必須放在的該層的。

 

30.如何讓Activity變成一個視窗?

答:在清單檔案AndroidManifest.xml中相應的<activity>標籤內設定屬性android:theme=”@android:style/Theme.Dialog”

 

31.後臺的Activity被系統回收怎麼辦?

除了在棧頂的Activity,其他的Activity都有可能在記憶體不足的時候被系統回收,一個Activity越處於棧底,被回收的可能性就越大。如果我們沒有覆寫onSaveInstanceState()方法,此方法的預設實現會自動儲存Activity中的某些狀態資料,比如Activity中各種UI空間的狀態。Android應用框架中定義的幾乎所有的UI控制元件都恰當的實現了onSaveInstanceState()方法,因此當Activity被摧毀和重建時,這些UI控制元件會自動儲存和恢復狀態資料。比如EditText控制元件會自動儲存和恢復輸入的資料,而CheckBox控制元件會自動儲存和恢復選中狀態。開發者只需要為這些控制元件指定一個唯一的ID(通過設定android:id屬性即可),剩餘的事情就可以自動完成了。如果沒有為控制元件指定ID,則這個控制元件就不會進行自動的資料儲存和恢復操作。
由上所述,如果我們需要覆寫onSaveInstanceState()方法,一般會在第一行程式碼中呼叫該方法的預設實現:super.onSaveInstanceState(outState)。

32.ListView優化?

答:1)、對convetView進行判空,是當convertView不為空的時候直接重新使用convertView

從而減少了很多不必要的View的建立

2)定義一個ViewHolder,將convetView的tag設定為ViewHolder,不為空時重新使用即可

3)、當ListView載入資料量較大時可以採用分頁載入和圖片非同步載入

 

33.IPC及其原理?

 

1).Binder通訊是如何實現的?

   1.Binder通訊是通過linux的binder driver來實現的,

   2.Binder通訊操作類似執行緒遷移(thread migration),兩個程序間IPC看起來就象是一個程序進入另一個程序執行程式碼然後帶著執行的結果返回;

1)IPC(Inter-Process Communication,程序間通訊),

aidl是 Android Interface definition language的縮寫,它是一種android內部程序通訊介面的描述語言,通過它我們可以定義程序間的通訊介面.編譯器可以通過副檔名為aidl的檔案生成一段程式碼,通過預先定義的介面達到兩個程序內部通訊程序的目的.

BroadcastReceiver也可以實現程序間通訊

ContentProvider 提供程序間資料共享 

2).Android的 Service工作流程

  1.Android虛擬機器啟動之前系統會先啟動service Manager程序;

  2.service Manager開啟binder驅動,並通知binder kernel驅動程式這個程序將作為System Service Manager;

  3.然後該程序將進入一個迴圈,等待處理來自其他程序的資料。

  4.使用者建立一個System service後,通過defaultServiceManager得到一個遠端ServiceManager的介面,通過這個介面我們可以呼叫addService函式將System service新增到Service Manager程序中;

  5.然後client可以通過getService獲取到需要連線的目的Service的IBinder物件,這個IBinder是Service的BBinder在binder kernel的一個參考,

  6.所以service IBinder 在binder kernel中不會存在相同的兩個IBinder物件,每一個Client程序同樣需要開啟Binder驅動程式。對使用者程式而言,我們獲得這個物件就可以通過binder kernel訪問service物件中的方法。

  7.Client與Service在不同的程序中,通過這種方式實現了類似執行緒間的遷移的通訊方式,對使用者程式而言當呼叫Service返回的IBinder介面後,訪問Service中的方法就如同呼叫自己的函式。

34.View如何重新整理?

安卓要更新介面不要在主執行緒中去做

如果是線上程thread中獲取到了新的資料,需要配合使用hanlder進行重新整理.

線上程中重新整理View用postinvalidate();

在UI執行緒中重新整理View的方法是invalidate()函式,

當呼叫執行緒處於空閒狀態時,調onDraw()重新整理介面

 

如果是listView重新整理資料,用adapter.notifyDataSetInvalidated();

adapter.notifyDataSetChanged();

35.DDMS與TraceView的區別?

DDMS是一個程式執行檢視器,在裡面可以看見執行緒和堆疊等資訊,TraceView是程式效能分析器 。

36.在Java中如何引入C語言?


java中利用JNI引用本地語言 (java native interface  java 本地介面)介面 。
1.在應用程式中定義本地介面(native)編譯成.h標頭檔案,交由C程式設計師實現,將.c實現通過NDk編譯成.so動態連結庫(windows下是.dll, linux下是.so,匯入專案中的libs/armeabi,程式碼中呼叫本地介面,
應用場景:音訊,拍攝車牌號

37.連結串列和陣列的區別?

陣列是將元素在記憶體中連續存放,由於每個元素佔用記憶體相同,可以通過下標迅速訪問陣列中任何元素。但是如果要在陣列中增加一個元素,需要移動大量元素,在記憶體中空出一個元素的空間,然後將要增加的元素放在其中。同樣的道理,如果想刪除一個元素,同樣需要移動大量元素去填掉被移動的元素。如果應用需要快速訪問資料,很少或不插入和刪除元素,就應該用陣列。

連結串列恰好相反,連結串列中的元素在記憶體中不是順序儲存的,而是通過存在元素中的指標聯絡到一起。比如:上一個元素有個指標指到下一個元素,以此類推,直到最後一個元素。如果要訪問連結串列中一個元素,需要從第一個元素開始,一直找到需要的元素位置。但是增加和刪除一個元素對於連結串列資料結構就非常簡單了,只要修改元素中的指標就可以了。如果應用需要經常插入和刪除元素你就需要用連結串列資料結構了。

二者都屬於一種資料結構
(1) 從邏輯結構角度來看
  a, 陣列必須事先定義固定的長度(元素個數),不能適應資料動態地增減的情況。當資料增加時,可能超出原先定義的元素個數;當資料減少時,造成記憶體浪費。
  b,連結串列動態地進行儲存分配,可以適應資料動態地增減的情況,且可以方便地插入、刪除資料項。(陣列中插入、刪除資料項時,需要移動其它資料項)
(2)從記憶體儲存角度來看
  a,(靜態)陣列從棧中分配空間, 對於程式設計師方便快速,但自由度小。
  b, 連結串列從堆中分配空間, 自由度大但申請管理比較麻煩.

  1. Hash表是什麼?有什麼用?

散列表(Hash table,也叫雜湊表),是根據關鍵碼值(Key value)而直接進行訪問的資料結構。也就是說,它通過把關鍵碼值對映到表中一個位置來訪問記錄,以加快查詢的速度。這個對映函式叫做雜湊函式,存放記錄的陣列叫做散列表。

給定表M,存在函式f(key),對任意給定的關鍵字值key,代入函式後若能得到包含該關鍵字的記錄在表中的地址,則稱表M為雜湊(Hash)表,函式f(key)為雜湊(Hash) 函式

作用:HASH表主要就是提供更快的查詢速度,簡單來說就是分桶。 

比如說你們學校的一個年級有很多班是吧? 那麼現在要查詢一位同學。如果不看班級直接找,就需要每個班級一個一個的查詢是不? 那現在因為分了班級,我們有一個函式可以通過名字產生它的班級號。比如說王勇,二班。 那麼現在我們直接hash( 王勇) = 2; 然後我們就直接從2班開始找。 如果2班有50個學生,那麼我們最多查詢50次對嗎? 好。假設你們年級一共有10個班,如果沒有這個hash函式,那麼直接找,最壞可能要查詢50*10=500次。!! 這個班級其實就是每個桶!! 這就是分桶。。。通過雜湊函式產生雜湊值,然後相同雜湊值的元素放在相同的桶裡邊。。。! 

這樣可以通過hash這個間接作用減少查詢的時間和次數!這就是它的意義!!

  1. 什麼是鎖?有什麼用?有哪些鎖?為什麼需要鎖?

鎖是為了保證安全性,如程式執行時保證另外的程式不能再對本程式所使用到的資料進行某些操作,版本軟體的“不能合併”檔案不能同時被兩人修改等。

鎖分為:執行緒鎖,資料庫鎖,SVN鎖等等

  1、當幾個執行緒都用到了某個量,但是這個量卻能影響程式的執行時就需要執行緒鎖來控制一次只能由一個執行緒訪問這個量。如果沒有使用執行緒鎖會出現爭用情況。

兩個或更多的執行緒或程序讀或寫一些共享資料,而最終結果取決於這些執行緒是如何被排程計時的。爭用情況可能會導致不可預見的結果和隱蔽的程式錯誤。 

2、資料庫鎖的作用是防止程式執行的時候其他的程式不能再對該程式所使用到的資料進行操作,保護資料的安全性。

 3、SVN鎖的作用是防止版本軟體中的“不能合併”的檔案(如:圖形檔案)不能被多人同時更改的時候進行鎖定,當一個人對其進行操作時,其他人不能對這個檔案再進行操作,保證了檔案的安全性。