當前位置:首頁 » 安卓系統 » android範例

android範例

發布時間: 2022-11-19 00:43:44

Ⅰ Android技術分享|Android 中部分內存泄漏示例及解決方案

內存泄漏:

舉例:

請注意以下的例子是虛構的

內存抖動

源自Android文檔中的 Memory churn 一詞,中文翻譯為內存抖動。

指快速頻繁的創建對象從而產生的性能問題。

引用Android文檔原文:

Java內存泄漏的根本原因是 長生命周期 的對象持有 短生命周期 對象的引用就很可能發生內存泄漏。

盡管短生命周期對象已經不再需要,但因為長生命周期依舊持有它的引用,故不能被回收而導致內存泄漏。

靜態集合類引起的內存泄漏


如果僅僅釋放引用本身(tO = null), ArrayList 依然在引用該對象,GC無法回收。

監聽器

在Java應用中,通常會用到很多監聽器,一般通過 addXXXXListener() 實現。但釋放對象時通常會忘記刪除監聽器,從而增加內存泄漏的風險。

各種連接

資料庫連接、網路連接(Socket)和I/O連接。忘記顯式調用 close() 方法引起的內存泄漏。

內部類和外部模塊的引用

內部類的引用是很容易被遺忘的一種,一旦沒有釋放可能會導致一系列後續對象無法釋放。此外還要小心外部模塊不經意的引用,內部類是否提供相應的操作去除外部引用。

單例模式

由於單例的靜態特性,使其生命周期與應用的生命周期一樣長,一旦使用不恰當極易造成內存泄漏。如果單利持有外部引用,需要注意提供釋放方式,否則當外部對象無法被正常回收時,會進而導致內存泄漏。

集合類泄漏

如集合的使用范圍超過邏輯代碼的范圍,需要格外注意刪除機制是否完善可靠。比如由靜態屬性 static 指向的集合。

單利泄漏

以下為簡單邏輯代碼,只為舉例說明內存泄漏問題,不保證單利模式的可靠性。


AppManager 創建時需要傳入一個 Context ,這個 Context 的生命周期長短至關重要。

1. 如果傳入的是 Application 的 Context ,因為 Application 的生命周期等同於應用的生命周期,所以沒有任何問題。

2. 如果傳入的是 Activity 的 Context ,則需要考慮這個 Activity 是否在整個生命周期都不會被回收了,如果不是,則會造成內存泄漏。

非靜態內部類創建靜態實例造成的內存泄漏


應該將該內部類單獨封裝為一個單例來使用。

匿名內部類/非同步線程


Runnable都使用了匿名內部類,將持有MyActivity的引用。如果任務在Activity銷毀前未完成,將導致Activity的內存無法被回收,從而造成內存泄漏。

解決方法:將Runnable獨立出來或使用靜態內部類,可以避免因持有外部對象導致的內存泄漏。

Handler造成的內存泄漏


Handler屬於TLS(Thread Local Storage)變數,生命周期與Activity是不一致的,容易導致持有的對象無法正確被釋放

當Android應用程序啟動時,該應用程序的主線程會自動創建一個Looper對象和與之關聯的MessageQueue。

當主線程中實例化一個Handler對象後,它就會自動與主線程Looper的MessageQueue關聯起來。所有發送到MessageQueue的Messag都會持有Handler的引用,所以Looper會據此回調Handle的handleMessage()方法來處理消息。只要MessageQueue中有未處理的Message,Looper就會不斷的從中取出並交給Handler處理。

另外,主線程的Looper對象會伴隨該應用程序的整個生命周期。

在Java中,非靜態內部類和匿名類內部類都會潛在持有它們所屬的外部類的引用,但是靜態內部類卻不會。

當該 Activity 被 finish() 掉時,延遲執行任務的 Message 還會繼續存在於主線程中,它持有該 Activity 的 Handler 引用,所以此時 finish() 掉的 Activity 就不會被回收了從而造成內存泄漏(因 Handler 為非靜態內部類,它會持有外部類的引用,在這里就是指 SampleActivity)。


避免不必要的靜態成員變數

對於BroadcastReceiver、ContentObserver、File、Cursor、Stream、Bitmap等資源的使用,應在Activity銷毀前及時關閉或注銷。

不使用WebView對象時,應調用`destroy()`方法銷毀。

Ⅱ Android-Ble藍牙開發Demo示例–掃描,連接,發送和接收數據,分包解包(附源碼)

萬物互聯的物聯網時代的已經來臨,ble藍牙開發在其中扮演著舉重若輕的角色。最近剛好閑一點,抽時間梳理下這塊的知識點。

涉及ble藍牙通訊的客戶端(開啟、掃描、連接、發送和接收數據、分包解包)和服務端(初始化廣播數據、開始廣播、配置Services、Server回調操作)整個環節以及一些常見的問題即踩過的一些坑。

比如
1、在Android不同版本或不同手機的適配問題,掃描不到藍牙設備
2、如何避免ble藍牙連接出現133錯誤?
3、單次寫的數據大小有20位元組限制,如何發送長數據

藍牙有傳統(經典)藍牙和低功耗藍牙BLE(Bluetooth Low Energy)之分,兩者的開發的API不一樣,本文主講Ble藍牙開發,傳統藍牙不展開,有需要的可以自行了解。

相對傳統藍牙,BLE低功耗藍牙,主要特點是快速搜索,快速連接,超低功耗保持連接和數據傳輸。

客戶端

服務端

Android4.3(API Level 18)開始引入BLE的核心功能並提供了相應的 API。應用程序通過這些 API 掃描藍牙設備、查詢 services、讀寫設備的 characteristics(屬性特徵)等操作。

BLE藍牙協議是GATT協議, BLE相關類不多, 全都位於android.bluetooth包和android.bluetooth.le包的幾個類:
android.bluetooth.
.BluetoothGattService 包含多個Characteristic(屬性特徵值), 含有唯一的UUID作為標識
.BluetoothGattCharacteristic 包含單個值和多個Descriptor, 含有唯一的UUID作為標識
.BluetoothGattDescriptor 對Characteristic進行描述, 含有唯一的UUID作為標識

.BluetoothGatt 客戶端相關
.BluetoothGattCallback 客戶端連接回調
.BluetoothGattServer 服務端相關
.BluetoothGattServerCallback 服務端連接回調

android.bluetooth.le.
.AdvertiseCallback 服務端的廣播回調
.AdvertiseData 服務端的廣播數據
.AdvertiseSettings 服務端的廣播設置
.BluetoothLeAdvertiser 服務端的廣播

.BluetoothLeScanner 客戶端掃描相關(Android5.0新增)
.ScanCallback 客戶端掃描回調
.ScanFilter 客戶端掃描過濾
.ScanRecord 客戶端掃描結果的廣播數據
.ScanResult 客戶端掃描結果
.ScanSettings 客戶端掃描設置

BLE設備分為兩種設備: 客戶端(也叫主機/中心設備/Central), 服務端(也叫從機/外圍設備/peripheral)
客戶端的核心類是 BluetoothGatt
服務端的核心類是 BluetoothGattServer 和 BluetoothLeAdvertiser
BLE數據的核心類是 BluetoothGattCharacteristic 和 BluetoothGattDescriptor

下面詳細講解下客戶端和服務端的開發步驟流程

安卓手機涉及藍牙許可權問題,藍牙開發需要在AndroidManifest.xml文件中添加許可權聲明:

在搜索設備之前需要詢問打開手機藍牙:

注意: BLE設備地址是動態變化(每隔一段時間都會變化),而經典藍牙設備是出廠就固定不變了!

通過掃描BLE設備,根據設備名稱區分出目標設備targetDevice,下一步實現與目標設備的連接,在連接設備之前要停止搜索藍牙;停止搜索一般需要一定的時間來完成,最好調用停止搜索函數之後加以100ms的延時,保證系統能夠完全停止搜索藍牙設備。停止搜索之後啟動連接過程;

BLE藍牙的連接方法相對簡單只需調用connectGatt方法;

參數說明

與設備建立連接之後與設備通信,整個通信過程都是在BluetoothGattCallback的非同步回調函數中完成;

BluetoothGattCallback中主要回調函數如下:

上述幾個回調函數是BLE開發中不可缺少的;

當調用targetdDevice.connectGatt(context, false, gattCallback)後系統會主動發起與BLE藍牙設備的連接,若成功連接到設備將回調onConnectionStateChange方法,其處理過程如下:

判斷newState == BluetoothGatt.STATE_CONNECTED表明此時已經成功連接到設備;

mBluetoothGatt.discoverServices();

掃描BLE設備服務是安卓系統中關於BLE藍牙開發的重要一步,一般在設備連接成功後調用,掃描到設備服務後回調onServicesDiscovered()函數,函數原型如下:

BLE藍牙開發主要有負責通信的BluetoothGattService完成的。當且稱為通信服務。通信服務通過硬體工程師提供的UUID獲取。獲取方式如下:

具體操作方式如下:

開啟監聽,即建立與設備的通信的首發數據通道,BLE開發中只有當客戶端成功開啟監聽後才能與服務端收發數據。開啟監聽的方式如下:

BLE單次寫的數據量大小是有限制的, 通常是20位元組 ,可以嘗試通過requestMTU增大,但不保證能成功。分包寫是一種解決方案,需要定義分包協議,假設每個包大小20位元組,分兩種包,數據包和非數據包。對於數據包,頭兩個位元組表示包的序號,剩下的都填充數據。對於非數據包,主要是發送一些控制信息。
監聽成功後通過向 writeCharacteristic寫入數據實現與服務端的通信。寫入方式如下:

其中:value一般為Hex格式指令,其內容由設備通信的藍牙通信協議規定;

若寫入指令成功則回調BluetoothGattCallback中的onCharacteristicWrite()方法,說明將數據已經發送給下位機;

若發送的數據符合通信協議,則服務端會向客戶端回復相應的數據。發送的數據通過回調onCharacteristicChanged()方法獲取,其處理方式如下:

通過向服務端發送指令獲取服務端的回復數據,即可完成與設備的通信過程;

當與設備完成通信之後之後一定要斷開與設備的連接。調用以下方法斷開與設備的連接:

源碼上傳在CSDN上了,有需要的可以借鑒。

=====> Android藍牙Ble通訊Demo示例源碼–掃描,連接,發送和接收數據,分包解包

BLE單次寫的數據量大小是有限制的,通常是20位元組,可以嘗試通過requestMTU增大,但不保證能成功。分包寫是一種解決方案,需要定義分包協議,假設每個包大小20位元組,分兩種包,數據包和非數據包。對於數據包,頭兩個位元組表示包的序號,剩下的都填充數據。對於非數據包,主要是發送一些控制信息。
總體流程如下:
1、定義通訊協議,如下(這里只是個舉例,可以根據項目需求擴展)

2、封裝通用發送數據介面(拆包)
該介面根據會發送數據內容按最大位元組數拆分(一般20位元組)放入隊列,拆分完後,依次從隊列里取出發送

3、封裝通用接收數據介面(組包)
該介面根據從接收的數據按協議里的定義解析數據長度判讀是否完整包,不是的話把每條消息累加起來

4、解析完整的數據包,進行業務邏輯處理

5、協議還可以引入加密解密,需要注意的選演算法參數的時候,加密後的長度最好跟原數據長度一致,這樣不會影響拆包組包

一般都是Android版本適配以及不同ROM機型(小米/紅米、華為/榮耀等)(EMUI、MIUI、ColorOS等)的許可權問題

藍牙開發中有很多問題,要靜下心分析問題,肯定可以解決的,一起加油;

Ⅲ 為什麼我導入的android sdk范常式序全是打叉叉的

你先創建一個android項目,看看能不能正常工作,是不是顯示打叉,如果連創建的工程本身都是打叉的,那就意味著你的ADT是不完整的或者你的SDK沒有在線更新一些toos工具。

此外你是通過這種方式導入的嗎?

如果不是,請按ctrl+N打開新建窗口,選擇「Android」中的「Android Project from existing code」,點擊「下一步」,選擇代碼工程目錄,OK,這才是正確的導入方式,你看看是不是這么來的。

Ⅳ Google Android SDK開發範例大全的內容簡介

本書在上一版的基礎上,以Android手機應用程序開發(採用Android SDK 2.1)為主題,通過160多個範例全面且深度地整合了手機、網路及服務等多個開發領域,為讀者提高程序設計功力提供了很大的幫助。
全書共分10章,主要以範例集的方式來講述Android的知識點,詳細介紹了開發Android的人機交互界面、Android常用的開發控制項、使用Android手機收發簡訊等通信服務、開發Android手機的自動服務功能和娛樂多媒體功能以及整合Android與Google強大的網路服務等內容。隨書光碟中包括了所有範例的程序代碼。
本書講述由淺入深,由Android的基礎知識到實際開發應用,結構清晰、語言簡潔,非常適合Android的初學者和Android的進階程序開發者閱讀參考。

Ⅳ 百度地圖的Android示常式序怎麼使用

如果你不會,請加入QQ718081228428,我為你解答!!!!!!

Ⅵ android範例,猜猜雞蛋在哪只鞋子里,再玩一次時 reset() 方法看不懂啊循環3次,但是隨機數只有0,1啊,

必須隨機數只有0,1。Math.random()產生的是[0,1)之間的double類型的偽隨機數,是大於等於小於1的,你上面乘以2後,它的范圍也是[0,2),只能取0,1這個兩個,取不到2的。所以你的隨機數永遠都是0,1這個兩個數。你要乘以3才對。[0,3)這樣就能取到2了,隨機數就會有0,1,2

Ⅶ 《Android開發範例代碼大全》源碼

這個怎麼可能有 除非買書附送的

Ⅷ Android SDK範例如何在手機上測試

Eclipse開發的Android程序可以直接在手機上運行。
運行方式:
1. 手機打開 USB調式模式(具體:「設置」->「應用程序」->「開發」->「USB調試」)(不同的手機操作可能打開方式不一樣)。
2. 將手機連接到電腦。
3. 電腦上安裝手機USB驅動程序。
4. 運行android 應用。
點擊工程 run as android application後,系統就會查找已經連接到電腦的設備,選擇已經連接的設備即可運行在手機上了。

Ⅸ android 5.0開發範例代碼大全第4版怎麼樣

基於最新的Android 5.0版本分析
隨書贈送「極客學院」2個月全部課程免費VIP學習卡(獲取方式見本書封底)
小米電視系統軟體部總監、原Motorola軟體總監、德信無線軟體部經理等專家鼎力推薦
全面細致講解了系統調用、內存管理、管道、線程管理、同步機制、Log模塊、Binder驅動、同步和消息機制、Init進程、Zygote進程、資源管理、應用管理、組件管理、管理進程、圖形顯示系統、窗口系統、輸入管理系統、電源管理、存儲系統、網路系統、音頻系統、SELinux模塊、最新ART虛擬機、垃圾回收、Recovery模塊、內存泄露等核心模塊在Android系統中的原理。
書中盡可能詳細地給出了主要模塊的架構、原理和主幹實現,很多模塊前後能相互印證用以幫助讀者學習,希望通過本書幫助讀者快速理解內核的設計思想、獲得對Android系統進行二次開發的能力。

內容簡介
書籍
計算機書籍
《深入解析Android 5.0系統》詳細剖析了最新Android 5.0 系統主要框架的原理和具體實現。本書共24章,覆蓋了Android 5.0 系統中、下層重要的模塊,對於每個模塊都詳細介紹了它們的架構、原理及代碼實現等各個方面,盡量讓讀者知其然,又知其所以然,達到學以致用的目的。主要內容為:
Android Build系統核心、Android的Bionic、系統調用的實現方法、Android的Binder、Binder應用層的核心類、Android 的JNI、Android的同步和消息機制、進程間的消息傳遞、Android的Init進程、Android的Zygote進程、Android的資源管理、Android的SystemServer進程、Android的應用管理、Android的組件管理、Android的多用戶模式、Android的圖形顯示系統、Android的窗口系統、Android 的輸入管理、Android的電源管理、Android的存儲系統、Android的網路管理框架、Android的音頻系統、Android的SELinux模塊、Dalvik和ART虛擬機、Android的Recovery模塊、Android的調試方法、內存泄露的分析、Android的自動化測試等系統的核心知識。
在書中盡可能詳細地給出了代碼的注釋、各種屬性和常量的解釋,以及各種系統中使用的文件格式的介紹,希望讀者能通過本書,獲得對Android 5.0系統進行二次開發的能力,本書是進行系統開發人員的案頭必備書。
《深入解析Android 5.0系統》面向的讀者主要是進行系統開發的工程師,包括應用開發工程師、ROM開發工程師和各種使用Android作為開發平台的TV和可穿戴式設備(Wear)的開發工程師。本書也可以作為大專院校相關專業師生的學慣用書及培訓學校教材。

Ⅹ Android中點擊事件功能實現示例

第一種點擊事件

在xml中設置onclick屬性

 android:onClick="myOnclick"

第二種;獲取Button然後一個一個單獨綁定點擊事件

http://schemas.android.com/apk/res/android"

    xmlns:tools=" http://schemas.android.com/tools "

    android:layout_width="match_parent"

    android:layout_height="match_parent"

   android:orientation="vertical" >

      < android:id="@+id/btn_imgBtn"

        android:layout_width="fill_parent"

        android:layout_height="wrap_content"

        android:onClick="myOnclick"

        android:text="imageButton"

        />

        <android:id="@+id/btn_imgView"

        android:layout_width="fill_parent"

        android:layout_height="wrap_content"

        android:onClick="myOnclick"

        android:text="imageView"

        />

public class MainActivity extends ActionBarActivity {

 private Button btnImageBtn;

 private Button btnImageView;

    @Override

    protected void onCreate(Bundle savedInstanceState) {

        super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

        btnImageBtn = (Button) findViewById(R.id.btn_imgBtn);

        btnImageView =  (Button) findViewById(R.id.btn_imgView);

 btnImageBtn.setOnClickListener(new OnClickListener() {

   @Override

   public void onClick(View v) {

    Toast.makeText(MainActivity.this, "點擊ImageButton", Toast.LENGTH_SHORT).show();

   }

  });

        btnImageView.setOnClickListener(new MyListener());

    }

第三種:寫一個類(MyListener)實現OnClickListener介面,然後Button在設置onclickListener的時候new一個MyListener

btnImageView.setOnClickListener(new MyListener());

 class MyListener implements OnClickListener{

  @Override

  public void onClick(View view) {

   switch (view.getId()) {

   case R.id.btn_imgBtn:

    Toast.makeText(MainActivity.this, "點擊ImageButton", Toast.LENGTH_SHORT).show();

    break;

         case R.id.btn_imgView:

          Toast.makeText(MainActivity.this, "點擊imageView", Toast.LENGTH_SHORT).show();

    break;

   } 

第四種:整個類(MianActivity)實現onclickListener的介面

跳轉界面

Intent:意圖,用於訪問android中的組件

用Intent跳轉界面(activity)

第一步:new一個Intent()

Intent intent1 = new Intent(MainActivity.this,ImageButtonActivity.class);

startActivity(intent1);

 public void myOnclick(View view){

     switch (view.getId()) {

  case R.id.btn_imgBtn:

   Intent intent1 = new Intent(MainActivity.this,ImageButtonActivity.class);

   startActivity(intent1);

   break;

        case R.id.btn_imgView:

         Intent intent2 = new Intent(MainActivity.this,ImageViewActivity.class);

   startActivity(intent2);

   break;

Intent intent = new Intent(當前的activity,跳轉到的acticvity.class);

startActivity(intent);

3.ImageView

展示方式:scaleType:

4.ImageButton:

觸摸事件:當控制項或者屏幕唄觸摸的時候,產生的反應

public boolean onTouchEvent(MotionEvent event) {



imageButton:現在已經唄button代替,用於展示圖片的按鈕。不能顯示文字。

imageView

scaleType:圖片展示的方式

 fitStart:展示在控制項的上方

 fitCenter:展示在控制項的中間

 fitEnd;展示在控制項的下方

 fitXY:不按照比例拉伸

 matrix:矩陣模式

matrix可以設置圖片旋轉,縮放。移動

獲取圖片的高度和寬度

int h = imgView.getDrawable().getIntrinsicHeight();

int w = imgView.getDrawable().getIntrinsicWidth();

 Matrix m = new Matrix();

m.postRotate(45);

m.postRotate(45, w/2, h/2);

imgView.setImageMatrix(m);

移動事件:

按下:MotionEvent.ACTION_DOWN

抬起:MotionEvent.ACTION_UP

移動:MotionEvent.ACTION_MOVE

獲取當前的移動事件,

event.getAction()

http://schemas.android.com/apk/res/android"

    xmlns:tools=" http://schemas.android.com/tools "

    android:layout_width="match_parent"

    android:layout_height="match_parent"

    >

        android:id="@+id/img_01"

        android:layout_width="fill_parent"

        android:layout_height="fill_parent"

        android:src="@drawable/ss"

        android:scaleType="fitXY"/>

        android:id="@+id/img_02"

        android:layout_width="fill_parent"

        android:layout_height="fill_parent"

        android:src="@drawable/gl"

        android:visibility="gone"

        android:scaleType="fitXY"/>

        android:layout_width="wrap_content"

        android:layout_height="wrap_content"

        android:src="@drawable/bird"

        android:layout_gravity="center"

        />

         android:layout_width="fill_parent"

         android:layout_height="wrap_content"

         android:textSize="20sp"

         android:textColor="#ff0000"

         android:gravity="center"

         android:text="小鳥飛"/>

public class MainActivity extends Activity {

 private ImageView img01;

 private ImageView img02;

 @Override

 protected void onCreate(Bundle savedInstanceState) {

  super.onCreate(savedInstanceState);

  setContentView(R.layout.activity_main);

  img01 = (ImageView) findViewById(R.id.img_01);

  img02 = (ImageView) findViewById(R.id.img_02);

 }

 @Override

 public boolean onTouchEvent(MotionEvent event) {

  //System.out.println("被摸了");

  if(event.getAction()==MotionEvent.ACTION_UP){

   Log.v("TAG", "被抬起來");

   if(img01.getVisibility()==View.VISIBLE){

    img01.setVisibility(View.GONE);

    img02.setVisibility(View.VISIBLE);

   }else{

    img01.setVisibility(View.VISIBLE);

    img02.setVisibility(View.GONE);

   }

  }else if(event.getAction()==MotionEvent.ACTION_DOWN){

   Log.v("TAG", "被按下了");

  }else if(event.getAction()==MotionEvent.ACTION_MOVE){

   Log.v("TAG", "移動了");

  }

  return super.onTouchEvent(event);

 }

熱點內容
yum內核源碼 發布:2025-03-05 09:27:41 瀏覽:93
x86編程 發布:2025-03-05 09:24:22 瀏覽:172
怎麼支付寶信用卡提現密碼 發布:2025-03-05 09:21:20 瀏覽:118
月神腳本圈 發布:2025-03-05 09:13:44 瀏覽:177
62批量操作腳本 發布:2025-03-05 08:52:57 瀏覽:609
java證書加密 發布:2025-03-05 08:45:44 瀏覽:239
給定演算法 發布:2025-03-05 08:45:43 瀏覽:94
視頻存儲碼流 發布:2025-03-05 08:30:52 瀏覽:894
六龍爭霸腳本輔助 發布:2025-03-05 08:25:56 瀏覽:580
es存儲視頻 發布:2025-03-05 08:01:31 瀏覽:598