1. 程式人生 > >搭建一個應用程式框架-做點什麼

搭建一個應用程式框架-做點什麼

    以前只做過模組功能的開發,在開源專案或者別人搭建的專案框架下敲碼。突然讓我來搭建一個app的框架,竟然不知道如何下手了!鬱悶,好吧先從網上收集了一些資料看看。好吧,拿來主義一篇來自csdn的部落格

1、一些概念

模式的定義:

每個模式都描述了一個在我們的環境中不斷出現的問題,然後描述了該問題的解決方案的核心。通過這種方式,你可以無數次地使用那些已有的解決方案,無需在重複相同的工作。

什麼是設計模式?

設計模式是在某種特別的情況下,針對某種問題的某種典型、通用的解決方法。

我們是需要適當瞭解並學習一些設計模式,在程式開發過程中,總是會涉及到一些框架設計,模組設計之類的東西,如果能很好理解並執行設計模式,你所設計的模組或框架將會要穩定得多,因為這些設計模式它們都是通用的解決方案,是經過實踐經驗了的。

比如說,在程式裡,可能會有通知模組,A模組的資料發生變化,B模組需要得到通知,對於這樣的需要,你可能會想到用"廣播","訊息"或者"回撥"的方式來解決,的確,剛才我所說的那三種也能解決,但是,這三種都是存在一些缺點,比如說廣播,用Intent來傳輸資料很困難,對於"訊息",無法很好的跟蹤,對於"回撥",有可能你A與B模組根本不可相互訪問。此時,如果你會用觀察者模式的問題,這種問題可以很輕鬆解決。

當然,這裡是需要具體問題具體分析的,我主要的意思就是說,要適當利用模式,我們不能為了用模式而去用模式,我們是要用模式來解決我們實際的問題。

(ps,應為對設計模式知道的也不多,程式中會設計單例模式+觀察者模式。。其他的模式還需要學習後再用)

概念完整性

關於概念完整性,在《人月神話》一書在有大量的闡述,這裡,我把我的理解寫出來,與大家分享。

1)概念完整性是系統設計中最重要的考慮因素。當你的系統規模越大,這一點體現得越明顯。

2)為了獲取概念的完整性,設計必須由一個人或者具有共識的小型團隊來完成。這一點很好理解,關於設計,可以讓所有的人蔘與,但是決定權在少數人手裡,如果大家都想參與設計,這是根本沒有辦法保證系統設計是統一完整的。

3)要獲得概念上的完整性,就必須有人控制這些概念,類似於貴族的專制統治。這裡,對於團隊中的專案經理或架構師必須對專案有絕對的權威,不然,這個專案裡面的就無法統一號令。

4)概念完整性表現有:(ps:這個還真沒有,需求目前是對比專案經理要求和web端功能新增)

    - 開發過程中,需求、設計、編碼的一致性
    - 整個程式具有統一的風格,比如對話方塊樣式,按鈕風格,色調等UI元素
    - 整個程式具體統一的結構,比如不同模組訪問網路,它們的呼叫方式一致,例如非同步訪問都用回撥方式通知結果,相同的功能應該提取成共通模組。
    - 開發人員能很好的執行需求人員和設計人員的意圖。
    - 有完整的文件,需求文件,設計文件,測試文件,處理流程的文件等。

如何保持概念完整性

    - 在制度上給予保證,產品的負責人必須建立技術上的絕對權威
    - 技術負責人員(SE,SL)必須嚴格執行專案的需求,設計,必須深入到編碼細節
    - 在不同階段,保持與所有人員的持續溝通,鼓勵開發人員提意見。
    - 讓開發人員參與設計,但不決定設計
    - 通過持續的反饋和溝通來實現模組重用

2、設計之前應該做什麼

2.1 共通類的設計(ps:這個很有必要)

2.1.1 Widget設計

  • TextView
  • EditText
  • Button
  • Title bar
  • Tool bar
  • ...

      為什麼要提供這些共通控制元件?

  • 統一字型大小,如App字型不隨系統字型變化而變化
  • 統一UI式樣,如Button, EditText具有相同的背景等
  • 複用程式碼

2.1.2 Adapter Items

  • 根據式樣,提取需要在AdapterView中顯示的Item
  • 簡單的複合佈局
  • 自繪製,從而提高滑動效能
    - ListView中放Gallery時,提高上下滑動效能
    - 儘量優化繪製

       資料驅動

  • Adapter Items提供核心的方法
    - setData(Object data)
    - getData();
  • Adapter#getView實現更加簡單
    - 實現簡單
    - 不會因為UI變化而變化

下面程式碼示例了Adapter#getView()方法的實現,它返回BookView,BookView提供方法來接收資料,至於BookView的顯示,則根據設定的資料來顯示,這就是資料驅動UI。

[java] view plaincopyprint?
  1. @Override
  2. public View getView(int position, View convertView, ViewGroup parent) { 
  3. if (null == convertView) { 
  4.         convertView = new BookView(getContext()); 
  5.         convertView.setLayoutParameter(new AbsListView.LayoutParameter(150, 150)); 
  6.     } 
  7.     Book book = m_bookList.get(position); 
  8.     BookView bookView = (BookView)convertView; 
  9.     bookView.setBook(book); 
  10. return convertView; 
@Override
public View getView(int position, View convertView, ViewGroup parent) {

    if (null == convertView) {
        convertView = new BookView(getContext());
        convertView.setLayoutParameter(new AbsListView.LayoutParameter(150, 150));
    }

    Book book = m_bookList.get(position);
    BookView bookView = (BookView)convertView;
    bookView.setBook(book);

    return convertView;
}

2.1.3 Dialog

  • 擴充套件於Dialog類
  • 提供Dialog關閉的事件
  • Dialog的高度隨內容的變化而變化
  • 可以設定按鈕的文字,可見性,字型等方法
  • 設定按鈕點選事件的listener
  • 要考慮對話方塊的三個屬性:Title, Content area, Action buttons

2.1.4 Utility

  • Log
  • DateFormat
  • Bitmap
  • Notification
  • Shared Preference
  • Environment
  • Device
  • ...

2.2 Task管理

執行緒只是一種機制,保證我們要完成的任務不執行在UI執行緒(也就是說不阻塞UI),完成的任務才是我們關注的核心,因此,我們可以通過設計,把執行緒封裝,讓使用者根本感覺不到是執行緒,他只用關心他要做的事情就行了。
這裡,我們可以設計一種"非同步鏈式呼叫"的框架,把執行緒進行了封裝。使用都只需要這樣用:

[java] view plaincopyprint?
  1. new TaskManager() 
  2. .next(task1) 
  3. .next(task2) 
  4. .next(task3). 
  5. .execute(); 
new TaskManager()
.next(task1)
.next(task2)
.next(task3).
.execute();

這裡,task1, task2, task3是順序執行的,舉個例子:我們要訪問網路,取得一個圖片,使用這個TaskManager我們需要3個task,

task1:顯示一個ProgressDialog。

task2:訪問網路,建立bitmap。

task3:關閉對話方塊,顯示bitmap。

這一點,可以參考CoreLib工程中的task.TaskManager類。

關於TaskManager,有以下幾點需要注意:

  • 封裝了執行緒
  • 讓呼叫者只關注自己的業務處理
  • 保證順序鏈式地執行某一個任務
  • 上一個任務的輸出,作為下一個任務的輸入
  • 能暫停、恢復任何一個任務

2.3 快取設計(ps:根據之前專案經驗,避免oom,我打算選擇imageLoad開源庫)

  • 把記憶體佔用量大的物件存放在快取中,如bitmap
  • 利用了LruCache類來實現
  • 利用了AsyncTask類來載入bitmap
  • 不用再手動釋放bitmap記憶體,該操作有風險
  • 不用再關心AbsListView的scroll狀態

關於快取的更多詳細細節,請參考[ 請參考CoreLib工程中的cache包 ]。

這樣做,有什麼好處, 不用再手動釋放bitmap內在,該操作有風險,因為該bitmap是否有View引用,如果當一個View在試圖繪製一個已經回收的bitmap,這裡會丟擲異常。

2.4 執行緒管理

無訊息迴圈的執行緒:

[java] view plaincopyprint?
  1. new Thread(null, new Runnable() { 
  2. publicvoid run() { 
  3. // Do you works.
  4.     } 
  5. }, "Thread_name_xxx").start(); 
new Thread(null, new Runnable() {
    public void run() {
        // Do you works.
    }

}, "Thread_name_xxx").start();

什麼情況下使用這種執行緒:

  • 做完一件事情就結束,這件事發生頻率不高,比如從SD card中讀取圖片資料
  • 不需要複用執行緒

在使用執行緒,最好給執行緒加上名字,這樣利用高度與跟蹤。

  有訊息迴圈的執行緒:

這樣的執行緒擁有訊息迴圈,當訊息佇列中沒有訊息時,這個執行緒會被掛起。我們要做一件事情時,只需要給它傳送一個訊息就行了。

這種情況通常是為了複用執行緒,不用頻繁建立執行緒,比如音樂播放器程式,專門啟動一個有訊息迴圈的執行緒來獲得音樂的專輯圖片。

我們通常還要建立一個與這個執行緒的訊息迴圈(Looper)相關聯的Handler,由它來處理訊息,注意,這做的事情是執行在後臺執行緒的。

3,程式框架如何設計

Android程式的結構

  • UI層
    • 資料展示與管理
    • 使用者互動
    • 繪製
    • Adapter
  • 業務邏輯層
    • 持久化資料(記憶體中,相當於全域性資料)
    • 資料加式(資料層的資料有時候需要進行加工成UI層需要的資料)
    • 資料變化的通知機制
  • 資料層
    • 資料訪問(DB,檔案,網路等)
    • 快取(圖片,檔案等)
    • 配置檔案(shared perference)

下面,我試著畫了一個Android程式的結構,如果有不好的地方,歡迎指正。


   

4,一些基本原則

下面列出一些通常的原則,我們應當在開發過程中遵循,歡迎補充與指正。

4.1 提供initialize()方法

在Activity.onCreate()或者View的構造方法中呼叫,在以後看程式碼時,人們通常首先會去找initialize()這樣的方法。

4.2 封裝點選事件

把View的點選事件,提成方法,這樣在listener處只是一個方法呼叫者,一般的事件封裝為:onXXXClick(View v)。

4.3 設計一個BaseActivity類

讓所有的Activity都繼承自BaseActivity類,這樣,我們可以做很多有用的事情

  • 定義共通屬性
  • 顯示共通對話方塊(Progress dialog)
  • 取得top activity
  • 可以手動管理啟動的activity

4.4 設計Application類

  • 存全域性資料,比top activity, application context。

4.5 異常處理

  • 報告功能是處理異常的精髓
  • 在finally塊中執行清理操作
  • 不要用try-catch-finally來判斷業務邏輯
  • 考慮設計自定義的異常類

4.6 標註的使用

  • 重寫的方法一定要加@Override
  • 不使用的方法,不要刪除,可以標記為@Deprecated,這個做法在維護型的專案中特別有用。

4.7 註冊與反註冊

  • 區域性廣播
  • 各種listener
  • Service等

4.8 封裝Bitmap操作

我們應當把Bitmap操作封裝起來,比如從檔案載入,儲存,網路下載,動態計算sample size等。有了封裝後,我們可以對其集中優化。

4.9 繪製處理

一定要注意繪製方面的東西,不要在onDraw()/onTouchEvent()中建立新物件。

相關推薦

搭建一個應用程式框架-什麼

    以前只做過模組功能的開發,在開源專案或者別人搭建的專案框架下敲碼。突然讓我來搭建一個app的框架,竟然不知道如何下手了!鬱悶,好吧先從網上收集了一些資料看看。好吧,拿來主義一篇來自csdn的部落格 1、一些概念 模式的定義: 每個模式都描述了一個在我們的環境中不斷

一個javaWeb程式設計師一個桌面小應用的總結

CSDN的部落格編輯器太讓人受不了,原本好好的格式排版,粘上去全亂套了,怎麼調怎麼亂,今天試試Markdown,如果效果不錯,今後的部落格都用Markdown寫 最近專案要求我做一個工具 要求: 做一個工具,要能儲存系統地址、使用者名稱、密碼,實

利用maven搭建一個小型SSM框架的web程式

新建專案 新建maven project 三者全部勾選, 第一個是:建立一個簡單的maven工程 第二個是:選擇儲存路徑,只要選擇預設即可 第三個是:選擇工作區,自己隨便建立一個 即可 然後一路finsh 直到建立完成即可 如果創建出來的程

Vular開發手記#1:設計並實現一個拼插式應用程式框架

視覺化編(rxeditor)輯告一段落,在知乎上發了一個問題,詢問前景,雖然看好的不多,但是關注度還是有的,目前為止積累了21w流量,因為這個事,開心了好長一段時間。這一個月的時間,主要在設計製作Vular,基於Vuetify跟larval實現的,可拼插式應用框架。並且把RXEditor視覺化編輯也整合進來了

XWAF——Web應用程式框架

XWAF框架簡介 版本:V1.0.0.0 XWAF是一個基於java反射和Servlet 技術的Web應用程式框架。其英文全稱為“eXtensible Web Applica

Android應用程式框架講解

在我們的android的程式中會有很多的檔案,那麼這些檔案到底是有什麼作用呢? 我們編譯android專案,可以使用eclipse和AS,首先介紹一下eclipse中的框架 1、src檔案:存放的是應用程式使用到的java檔案 2、gen檔案:系統自動生成的目錄。不需要程式設計師進行

使用SpringBoot2.0搭建企業級應用開發框架(七)整合Shiro

準備 首先建立使用者許可權表 //使用者表 CREATE TABLE `sys_user` ( `id` varchar(32) NOT NULL COMMENT 'id', `username` varchar(64) DEFAULT NULL COMMENT '

使用SpringBoot2.0搭建企業級應用開發框架(六)使用Lombok

適用人 猿群 你還在為寫Getter/Setter而煩惱嗎?當你寫完一個有參建構函式後發現還需要再寫一個無參建構函式的時候是否有負面情緒產生?每個類中都要寫很長一段的Slf4j日誌物件使你感到憂傷嗎?那就一起來快樂地使用Lombok吧 基於註解提供多種在編譯時生產重複程式碼

使用SpringBoot2.0搭建企業級應用開發框架(五)多環境配置

血淚背景 在將甲方粑粑的想法實踐於世人之前,我們的專案至少要經歷 開發→測試→執行 3個環境,對於不同的環境我們可能需要連線不同的資料庫、設定不同的上傳路徑、呼叫不同地址的遠端服務等等,這就要求必須有不同的配置來滿足多環境需求 如果我們是通過打包前手動修改檔案內容的話,會由

使用SpringBoot2.0搭建企業級應用開發框架(四)配置LogBack日誌

前言 SpringBoot預設配置提供了對常用日誌的支援,如:Java Util Logging、Log4J、Log4J2和Logback,每種Logger都可以通過配置使用控制檯或者檔案輸出日誌內容 Logback是log4j框架的作者開發的新一代日誌框架,它效率更高、能夠適

Windows 中一個應用程式的啟動過程

轉載自:https://blog.csdn.net/cpp_mybest/article/details/80194158 1. Explorer.exe      Windows 能夠流行起來,很大一個原因是它有友好的使用者圖形介面,操作方便簡單,容易上手。在

Kubernetes系列之四:使用yaml檔案建立deployment來部署一個應用程式到k8s叢集

目的 從零開始開發一個超小的應用,將它打包成一個image,利用yaml檔案部署到kube叢集中。 具體的思路是:在開發環境中,打算建立一個node.js應用程式,因為使用它可以讓我的程式足夠簡單,然後使用dockerfile去建立一個docker image,再將它push到doc

flask入門--搭建一個Flask程式

新建一個HelloWorld.py # 匯入Flask類 from flask import Flask,render_template,abort,redirect # Flask函式接收一個引數name,它會指向程式所在的模組 app=Flask(__name__) # 裝飾器的作用是將路

手把手搭建一個springboot程式

簡介: 首先介紹一下springboot,Spring Boot是由Pivotal團隊提供的全新框架,其設計目的是用來簡化新Spring應用的初始搭建以及開發過程。該框架使用了特定的方式來進行配置,從而使開發人員不再需要定義樣板化的配置。通過這種方式,Spring Boot致力於在蓬勃發展的快速

獲取一個應用程式的執行次數,如果超過5次,給出使用次數已達上限請註冊的提示

Properties的練習題: 獲取一個應用程式的執行次數,如果超過5次,給出使用次數已達上限請註冊的提示。 思路: 計數器 每次程式啟動時都需要技術一次,並且是在原有的次數上進行計數 計數器是一個變數,一旦程式結束,計數器消失… 那麼再次啟動程式時,計數器又恢復預設值

[Ext JS6]應用程式框架介紹

Ext JS 對MVC 和MVVM兩種架構都支援。這兩種架構都是根據邏輯劃分程式的程式碼,兩種各有優劣。 MVC是什麼? Model, View , Control的首字母。 在MVC架構中,大多數類都是模型,檢視和控制器。 使用者與檢視互動,檢視顯示

android應用程式安裝後擊開啟帶來的問題

前幾天專案組反饋回來一個這樣的情況就是我在安裝應用之後點選了開啟 然後按home鍵 這個時候應用程式進入後臺 我點選手機桌面的時候圖片啟動應用程式 程式重新再次啟動 而不是後臺的程式返回到前臺;  /

使用spring+quartz+react+antd搭建一個定時任務框架

使用springboot搭建後端服務 springboot相對於傳統的spring來講可以大大加快web專案的開發,配置檔案的減少也能讓整個專案簡潔明瞭 1.功能清單 包括以下幾項功能: 執行定時任務 ,可以在專案啟動時指定一系列任務 管理任務 ,提供增刪改

Win32 程式開發:建立一個應用程式視窗

1)簡單介紹建立應用程式的步驟 1.設計一個視窗類 2.註冊這個視窗類 3.建立應用程式視窗 4.更新顯示視窗 5.應用程式訊息迴圈 2)下面根據這個步驟進行建立一個應用程式視窗吧 /* 標頭檔案 */ #include <windows.h>

應用程式框架實戰二十四:基礎查詢擴充套件

using Microsoft.VisualStudio.TestTools.UnitTesting; using Util.Domains.Repositories; namespace Util.Domains.Tests.Repositories { /// <summary&g