閑來無事在家偶然翻到了之前整理的文檔和面試要做到準(zhǔn)備路線,雖然內(nèi)容有點(diǎn)多,但是技多不壓身,多多益善
成都網(wǎng)站建設(shè)、網(wǎng)站制作的開發(fā),更需要了解用戶,從用戶角度來建設(shè)網(wǎng)站,獲得較好的用戶體驗(yàn)。成都創(chuàng)新互聯(lián)多年互聯(lián)網(wǎng)經(jīng)驗(yàn),見的多,溝通容易、能幫助客戶提出的運(yùn)營(yíng)建議。作為成都一家網(wǎng)絡(luò)公司,打造的就是網(wǎng)站建設(shè)產(chǎn)品直銷的概念。選擇成都創(chuàng)新互聯(lián),不只是建站,我們把建站作為產(chǎn)品,不斷的更新、完善,讓每位來訪用戶感受到浩方產(chǎn)品的價(jià)值服務(wù)。本部分內(nèi)容是關(guān)于Android進(jìn)階的一些知識(shí)總結(jié),涉及到的知識(shí)點(diǎn)比較雜,不過都 是面試中幾乎常問的知識(shí)點(diǎn),也是加分的點(diǎn)。 關(guān)于這部分內(nèi)容,可能需要有一些具體的項(xiàng)目實(shí)踐。在面試的過程中,結(jié)合具體自 身實(shí)踐經(jīng)歷,才能更加深入透徹的描繪出來
相關(guān)內(nèi)容后續(xù)GitHub更新,想沖擊金三銀四的小伙伴可以找找看看,歡迎star
(順手留下GitHub鏈接,需要獲取相關(guān)面試等內(nèi)容的可以自己去找)
https://github.com/xiangjiana/Android-MS
(VX:mm14525201314)
MVP,MVC,MVVM
此處延伸:手寫 mvp 例子,與 mvc 之間的區(qū)別,mvp 的優(yōu)勢(shì)
MVP 模式,對(duì)應(yīng)著 Model--業(yè)務(wù)邏輯和實(shí)體模型,view--對(duì)應(yīng)著 activity,負(fù)責(zé) View 的繪制以 及與用戶交互,Presenter--負(fù)責(zé) View 和 Model 之間的交互,MVP 模式是在 MVC
模式的基礎(chǔ)上, 將 Model 與 View 徹底分離使得項(xiàng)目的耦合性更低,在 Mvc
中項(xiàng)目中的 activity 對(duì)應(yīng)著 mvc
中的 C--Controllor
,而項(xiàng)目中的邏輯處理都是在這個(gè) C 中處理,同時(shí) View 與 Model 之間的交 互,也是也就是說,mvc
中所有的邏輯交互和用戶交互,都是放在 Controllor
中,也就是 activity 中。View 和 model 是可以直接通信的。而 MVP 模式則是分離的更加徹底,分工更加明確 Model--業(yè)務(wù)邏輯和實(shí)體模型,view--負(fù)責(zé)與用戶交互,Presenter 負(fù)責(zé)完成 View 于 Model 間的交互,MVP 和 MVC
大的區(qū)別是 MVC
中是允許 Model 和 View 進(jìn)行交互的,而 MVP 中很明顯,Model 與 View 之間的交互由 Presenter 完成。還有一點(diǎn)就是 Presenter
與 View 之 間的交互是通過接口的
MVP
,全稱 Model-View-Presenter 即模型-視圖-層現(xiàn)器。
提到MVP,就必須要先介紹一下它的前輩MVC,因?yàn)镸VP正是基于MVC的基礎(chǔ)發(fā) 展而來的。兩個(gè)之間的關(guān)系也是源遠(yuǎn)流長(zhǎng)。MVC
,全稱Model-View-Controller,即模型-視圖-控制器。 具體如下:View
: 對(duì)應(yīng)于布局文件Model
: 業(yè)務(wù)邏輯和實(shí)體模型Controllor
: 對(duì)應(yīng)于Activity
但是View
對(duì)應(yīng)于布局文件,其實(shí)能做的事情特別少,實(shí)際上關(guān)于該布局文件中的數(shù) 據(jù)綁定的操作,事件處理的代碼都在Activity
中,造成了Activity
既像View
又像 Controller
,使得Activity
變得臃腫。
而當(dāng)將架構(gòu)改為MVP以后,Presenter
的出現(xiàn),將Actvity
視為View層,Presenter
負(fù) 責(zé)完成View層與Model層的交互。
現(xiàn)在是這樣的: View
對(duì)應(yīng)于Activity
,負(fù)責(zé)View
的繪制以及與用戶交互 Model
依然是業(yè)務(wù)邏輯和實(shí)體模型 Presenter
負(fù)責(zé)完成View
于Model
間的交互 下面兩幅圖通過數(shù)據(jù)與視圖之間的交互清楚地展示了這種變化:MVC
模式下實(shí)際上就是Activty
與Model之間交互,View完全獨(dú)立出來了。MVP
模式通過Presenter
實(shí)現(xiàn)數(shù)據(jù)和視圖之間的交互,簡(jiǎn)化了Activity
的職責(zé)。同時(shí) 即避免了View
和Mode
l的直接聯(lián)系,又通過Presenter
實(shí)現(xiàn)兩者之間的溝通。
總結(jié): MVP
模式減少了Activity
的職責(zé),簡(jiǎn)化了Activity
中的代碼,將復(fù)雜的邏輯代 碼提取到了Presenter
中進(jìn)行處理,模塊職責(zé)劃分明顯,層次清晰。與之對(duì)應(yīng)的好 處就是,耦合度更低,更方便的進(jìn)行測(cè)試。
MVC
和MVP
的區(qū)別MVC
中是允許Model
和View
進(jìn)行交互的,而MVP
中很明顯,Model
與View
之間的 交互由Presenter
完成。還有一點(diǎn)就是Presenter
與View
之間的交互是通過接口 的。
還有一點(diǎn)注意: MVC
中V對(duì)應(yīng)的是布局文件,MVP
中V對(duì)應(yīng)的是Activity
。
大多數(shù)MVP
模式的示例都使用登錄案例進(jìn)行介紹。因?yàn)楹?jiǎn)單方便,同時(shí)能提現(xiàn)出 MVP
的特點(diǎn)。今天我們也以此例進(jìn)行學(xué)習(xí)。 使用MVP
的好處之一就是模塊職責(zé)劃 分明顯,層次清晰。 該例的結(jié)構(gòu)圖即可展現(xiàn)此優(yōu)點(diǎn)。
在本例中,M0del
層負(fù)責(zé)對(duì)從登錄頁面獲取地帳號(hào)密碼進(jìn)行驗(yàn)證(一般需要請(qǐng)求服 務(wù)器進(jìn)行驗(yàn)證,本例直接模擬這一過程)。 從上圖的包結(jié)構(gòu)圖中可以看出,Model 層包含內(nèi)容:
①實(shí)體類bean
②接口,表示Model層所要執(zhí)行的業(yè)務(wù)邏輯
③接口實(shí)現(xiàn)類,具體實(shí)現(xiàn)業(yè)務(wù)邏輯,包含的一些主要方法
下面以代碼的形式一一展開。
①實(shí)體類bean
public class User {
private String password;
private String username;
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
@Override
public String toString() {
return "User{" +
"password='" + password + '\'' +
", username='" + username + '\'' +
'}';
}
}
封裝了用戶名、密碼,方便數(shù)據(jù)傳遞。
②接口
public interface LoginModel {
void login(User user, OnLoginFinishedListener listener);
}
其中OnLoginFinishedListener
是presenter
層的接口,方便實(shí)現(xiàn)回調(diào)presenter
,通知presenter
業(yè)務(wù)邏輯的返回結(jié)果,具體在presenter
層介紹。
③接口實(shí)現(xiàn)類
public class LoginModelImpl implements LoginModel {
@Override
public void login(User user, final OnLoginFinishedListener l istener) {
final String username = user.getUsername();
final String password = user.getPassword();
new Handler().postDelayed(new Runnable() {
@Override public void run() {
boolean error = false;
if (TextUtils.isEmpty(username)){
listener.onUsernameError();//model層里面回調(diào)li stener
error = true;
}
if (TextUtils.isEmpty(password)){
listener.onPasswordError();
error = true;
}
if (!error){
listener.onSuccess();
}
}
}, 2000);
}
}
實(shí)現(xiàn)Model層邏輯:延時(shí)模擬登陸(2s),如果用戶名或者密碼為空則登陸失敗, 否則登陸成功。
視圖: 將Modle
層請(qǐng)求的數(shù)據(jù)呈現(xiàn)給用戶。一般的視圖都只是包含用戶界面(UI),而 不包含界面邏輯,界面邏輯由Presenter
來實(shí)現(xiàn)。
從上圖的包結(jié)構(gòu)圖中可以看出,View包含內(nèi)容:
①接口,上面我們說過Presenter與View交互是通過接口。其中接口中方法的定義是 根據(jù)Activity用戶交互需要展示的控件確定的。
②接口實(shí)現(xiàn)類,將上述定義的接口中的方法在Activity中對(duì)應(yīng)實(shí)現(xiàn)具體操作。
下面以代碼的形式一一展開。
①接口
public interface LoginView {
//login是個(gè)耗時(shí)操作,我們需要給用戶一個(gè)友好的提示,一般就是操作Progre ssBarvoid showProgress();
void hideProgress();
//login當(dāng)然存在登錄成功與失敗的處理,失敗給出提示 void setUsernameError();
void setPasswordError();
//login成功,也給個(gè)提示
void showSuccess();
}
上述5個(gè)方法都是presenter
根據(jù)model
層返回結(jié)果需要view執(zhí)行的對(duì)應(yīng)的操作。
②接口實(shí)現(xiàn)類
即對(duì)應(yīng)的登錄的Activity,需要實(shí)現(xiàn)LoginView
接口。
public class LoginActivity extends AppCompatActivity implements LoginView, View.OnClickListener {
private ProgressBar progressBar;
private EditText username;
private EditText password;
private LoginPresenter presenter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_login);
progressBar = (ProgressBar) findViewById(R.id.progress);
username = (EditText) findViewById(R.id.username);
password = (EditText) findViewById(R.id.password);
findViewById(R.id.button).setOnClickListener(this);
//創(chuàng)建一個(gè)presenter對(duì)象,當(dāng)點(diǎn)擊登錄按鈕時(shí),讓presenter去調(diào)用mode l層的login()方法,驗(yàn)證帳號(hào)密碼
presenter = new LoginPresenterImpl(this);
}
@Override
protected void onDestroy() {
presenter.onDestroy();
super.onDestroy();
}
@Override
public void showProgress() {
progressBar.setVisibility(View.VISIBLE);
}
.....
}
View
層實(shí)現(xiàn)Presenter
層需要調(diào)用的控件操作,方便Presenter
層根據(jù)Model
層返回 的結(jié)果進(jìn)行操作View層進(jìn)行對(duì)應(yīng)的顯示。
Presenter
是用作Model
和View
之間交互的橋梁。 從上圖的包結(jié)構(gòu)圖中可以看出, Presenter
包含內(nèi)容:
①接口,包含Presenter需要進(jìn)行Model和View之間交互邏輯的接口,以及上面提到 的Model層數(shù)據(jù)請(qǐng)求完成后回調(diào)的接口。
②接口實(shí)現(xiàn)類,即實(shí)現(xiàn)具體的Presenter類邏輯。
下面以代碼的形式一一展開。
①接口
public interface OnLoginFinishedListener {
void onUsernameError();
void onPasswordError();
void onSuccess();
}
當(dāng)Model
層得到請(qǐng)求的結(jié)果,需要回調(diào)Presenter
層,讓Presenter
層調(diào)用View
層的 接口方法。
public interface LoginPresenter {
void validateCredentials(User user);
void onDestroy();
}
登陸的Presenter
的接口,實(shí)現(xiàn)類為LoginPresenterImpl
,完成登陸的驗(yàn)證,以及銷 毀當(dāng)前view
。
②接口實(shí)現(xiàn)類
public class LoginPresenterImpl implements LoginPresenter, OnLog inFinishedListener {
private LoginView loginView;
private LoginModel loginModel;
public LoginPresenterImpl(LoginView loginView) {
this.loginView = loginView;
this.loginModel = new LoginModelImpl();
}
@Override
public void validateCredentials(User user) {
if (loginView != null) {
loginView.showProgress();
}
loginModel.login(user, this);
}
@Override
public void onDestroy() {
loginView = null;
}
@Override
public void onUsernameError() {
if (loginView != null) {
loginView.setUsernameError();
....
}
由于presenter
完成二者的交互,那么肯定需要二者的實(shí)現(xiàn)類(通過傳入?yún)?shù),或者 new)。 presenter
里面有個(gè)OnLoginFinishedListener
, 其在Presenter
層實(shí)現(xiàn),給Model
層 回調(diào),更改View
層的狀態(tài), 確保 Model
層不直接操作View
層。
示例展示:
View
與Model
并不直接交互,而是使用Presenter
作為View
與Model
之間的橋梁。其中Presenter
中同時(shí)持有View
層的Interface
的引用以及Model
層的引用,而View
層持有Presenter
層引用。當(dāng)View層某個(gè)界面需要展示某些數(shù)據(jù)的時(shí)候,首先會(huì)調(diào)用 Presenter
層的引用,然后Presenter
層會(huì)調(diào)用Model
層請(qǐng)求數(shù)據(jù),當(dāng)Model
層數(shù)據(jù)加 載成功之后會(huì)調(diào)用Presenter
層的回調(diào)方法通知Presenter
層數(shù)據(jù)加載情況,最后 Presenter
層再調(diào)用View
層的接口將加載后的數(shù)據(jù)展示給用戶。
相關(guān)內(nèi)容后續(xù)GitHub更新,想沖擊金三銀四的小伙伴可以找找看看,歡迎star
(順手留下GitHub鏈接,需要獲取相關(guān)面試等內(nèi)容的可以自己去找)
https://github.com/xiangjiana/Android-MS
(VX:mm14525201314)
另外有需要云服務(wù)器可以了解下創(chuàng)新互聯(lián)cdcxhl.cn,海內(nèi)外云服務(wù)器15元起步,三天無理由+7*72小時(shí)售后在線,公司持有idc許可證,提供“云服務(wù)器、裸金屬服務(wù)器、高防服務(wù)器、香港服務(wù)器、美國(guó)服務(wù)器、虛擬主機(jī)、免備案服務(wù)器”等云主機(jī)租用服務(wù)以及企業(yè)上云的綜合解決方案,具有“安全穩(wěn)定、簡(jiǎn)單易用、服務(wù)可用性高、性價(jià)比高”等特點(diǎn)與優(yōu)勢(shì),專為企業(yè)上云打造定制,能夠滿足用戶豐富、多元化的應(yīng)用場(chǎng)景需求。