導入
ブリッジモードは、抽象的なパーツを実装部品と分離して、すべてを独立して変化させることができます。
文章
ブリッジモードは、イベントモニタリングで最も一般的に使用されます。まずコードを見てみましょう。
コードコピーは次のとおりです。
addevent(element、 'click'、getbeerbyid);
関数getbeerbyid(e){
var id = this.id;
asyncrequest( 'get'、 'beer.uri?id =' + id、function(resp){
//コールバック応答。
console.log( 'リクエストビール:' + resp.responsetext);
});
}
上記のコードには、GetBeerbyIDが使用されるブラウザコンテキストを使用する必要があるという問題があります。これは、これを内部的に使用するためです。コンテキストが使用されない場合、停止します。したがって、一般に、少し経験豊富なプログラマーがプログラムを次の形式に変換します。
コードコピーは次のとおりです。
関数getBeerbyId(id、callback){
// ID経由でリクエストを送信し、データを返します
asyncrequest( 'get'、 'beer.uri?id =' + id、function(resp){
//コールバック応答
callback(resp.responsetext);
});
}
もっと実用的ですよね?まず、IDを自由に渡すことができ、カスタム処理機能にもコールバック関数も提供されます。しかし、これはブリッジングと何の関係があるのでしょうか?これは、次のコードが反映するものです。
コードコピーは次のとおりです。
AddEvent(要素、 'Click'、GetBeerByIdBridge);
関数getBeerByIdBridge(e){
getbeerbyid(this.id、function(ビール){
console.log( 'リクエストビール:'+ビール);
});
}
ここでは、GetBeerbyIdbridgeが定義するブリッジであり、抽象クリックイベントとGetBeerbyIdを接続するために使用され、同時にイベントソースのIDとカスタマイズされた呼び出し関数(Console.log出力)をパラメーターとしてGetBeerByID関数に渡します。
この例は少し単純に見えます。もう1つのより複雑な実用的な例を見てみましょう。
実際のXHR接続キュー
キューに多くのAJAXリクエストを保存するキューを構築したいと考えています。キューの使用は、主に、結合されたリクエストが最初に処理されることを確認する必要があるためです。いつでも、リクエストを一時停止し、リクエストを削除し、リクエストを再試行し、各リクエストのサブスクリプションイベントをサポートできます。
基本的なコア関数
公式開始の前に、いくつかのコアカプセル化関数を定義しましょう。最初に、最初は非同期リクエストの関数カプセル化です。
コードコピーは次のとおりです。
var asyncrequest =(function(){
function handledreadystate(o、callback){
var poll = window.setInterval(
関数 () {
if(o && o.readystate == 4){
Window.ClearInterval(Poll);
if(callback){
コールバック(o);
}
}
}、
50
);
}
var getxhr = function(){
var http;
試す {
http = new xmlhttprequest;
getXhr = function(){
新しいxmlhttprequestを返します。
};
}
catch(e){
var msxml = [
'msxml2.xmlhttp.3.0'、
'msxml2.xmlhttp'、
「Microsoft.xmlhttp」
];
for(var i = 0、len = msxml.length; i <len; ++ i){
試す {
http = new ActiveXObject(MSXML [i]);
getXhr = function(){
new ActiveXObject(MSXML [i])を返します。
};
壊す;
}
catch(e){}
}
}
httpを返します。
};
return function(method、uri、callback、postdata){
var http = getXhr();
http.open(method、uri、true);
HandledyState(http、callback);
http.send(postdata || null);
httpを返します。
};
})();
カプセル化された自己実行関数は一般的なAJAX要求関数であり、属性Ajaxを持っている人なら誰でもそれを理解できると思います。
次に、メソッド(関数)を追加する一般的な方法を定義します。
コードコピーは次のとおりです。
function.prototype.method = function(name、fn){
this.prototype [name] = fn;
これを返します。
};
最後に、アレイに2つのメソッドを追加します。1つはトラバーサル用、もう1つはフィルタリング用です。
コードコピーは次のとおりです。
if(!array.prototype.foreach){
array.method( 'foreach'、function(fn、thisobj){
var scope = thisobj ||ウィンドウ;
for(var i = 0、len = this.length; i <len; ++ i){
fn.call(scope、this [i]、i、this);
}
});
}
if(!array.prototype.filter){
array.method( 'filter'、function(fn、thisobj){
var scope = thisobj ||ウィンドウ;
var a = [];
for(var i = 0、len = this.length; i <len; ++ i){
if(!fn.call(scope、this [i]、i、this)){
続く;
}
a.push(this [i]);
}
aを返します。
});
}
一部の新しいブラウザはすでにこれらの2つの機能をサポートしているため(または一部のクラスライブラリはすでにサポートされています)、最初にそれらが既にサポートされているかどうかを判断する必要があり、既にサポートされている場合、処理されなくなります。
オブザーバーシステム
オブザーバーは、キュー内のイベントのプロセスで重要な役割を果たし、キューに登録されたときにイベントを購読できます(成功、失敗、保留中):
コードコピーは次のとおりです。
window.ded = window.ded || {};
ded.util = ded.util || {};
ded.util.observer = function(){
this.fns = [];
}
ded.util.observer.prototype = {
購読:function(fn){
this.fns.push(fn);
}、
登録解除:function(fn){
this.fns = this.fns.filter(
関数(el){
if(el!== fn){
Elを返します。
}
}
);
}、
火:function(o){
this.fns.foreach(
関数(el){
el(o);
}
);
}
};
キューの主な実装コード
まず、キューの主な属性とイベント代表を購読します。
コードコピーは次のとおりです。
ded.queue = function(){
//リクエストのキューを含みます。
this.queue = [];
// 3つの異なる状態で観測可能なオブジェクトを使用して、いつでもイベントを購読できるようにします
this.oncomplete = new ded.util.observer;
this.onfailure = new ded.util.observer;
this.onflush = new ded.util.observer;
//コアプロパティは、外部呼び出し中に設定できます
this.retrycount = 3;
this.currentretry = 0;
this.paused = false;
this.timeout = 5000;
this.conn = {};
this.timer = {};
};
次に、ded.queue.methodのチェーンコールを通じて、多くの利用可能な方法がキューに追加されます。
コードコピーは次のとおりです。
ded.queue。
メソッド( 'フラッシュ'、function(){
//フラッシュメソッド
if(!this.queue.length> 0){
戻る;
}
if(this.paused){
this.paused = false;
戻る;
}
var that = this;
this.currentretry ++;
var abort = function(){
that.conn.abort();
if(that.currentretry == that.retrycount){
that.onfailure.fire();
that.currentretry = 0;
} それ以外 {
that.flush();
}
};
this.timer = window.settimeout(abort、this.timeout);
var callback = function(o){
window.cleartimeout(that.timer);
that.currentretry = 0;
that.queue.shift();
that.onflush.fire(o.responsetext);
if(that.queue.length == 0){
that.oncomplete.fire();
戻る;
}
//フラッシュするための再帰コール
that.flush();
};
this.conn = asyncrequest(
this.queue [0] ['method']、
this.queue [0] ['uri']、
折り返し電話、
this.queue [0] ['params']
);
})。
方法( 'setretryCount'、function(count){
this.retrycount = count;
})。
方法( 'setimeout'、function(time){
this.timeout = time;
})。
方法( 'add'、function(o){
this.queue.push(o);
})。
方法( 'Pause'、function(){
this.paused = true;
})。
方法( 'dequeue'、function(){
this.queue.pop();
})。
メソッド( 'clear'、function(){
this.queue = [];
});
コードはよく見えるので、折りたたんだ後、フラッシュ、settryCount、setimeout、add、pause、dequeue、および明確な方法でキューに実際に定義されていることがわかります。
簡単な呼び出し
コードコピーは次のとおりです。
var q = new ded.queue;
//再生の数を少し高く設定して、遅い接続に対処する
Q.SetTretryCount(5);
//タイムアウト時間を設定します
Q.Settimeout(1000);
// 2つのリクエストを追加します。
Q.Add({
方法:「取得」、
uri: '/path/to/file.php?ajax=true'
});
Q.Add({
方法:「取得」、
uri: '/path/to/file.php?ajax=true&woe=me'
});
// Queueのフラッシュ
Q.Flush();
//キューを一時停止し、残りのものを保存します
Q.Pause();
// クリア。
Q.CLEAR();
// 2つのリクエストを追加します。
Q.Add({
方法:「取得」、
uri: '/path/to/file.php?ajax=true'
});
Q.Add({
方法:「取得」、
uri: '/path/to/file.php?ajax=true&woe=me'
});
//キューから最後のリクエストを削除します。
q.dequeue();
//もう一度フラッシュします
Q.Flush();
橋はどこですか?
上記のコールコードには橋がないので、橋はどうですか?以下の完全な例をご覧ください。どこにでも橋があることがわかります。
コードコピーは次のとおりです。
<!doctype html public " - // w3c // dtd html 4.01 // en"
"http://www.w3.org/tr/html4/strict.dtd">
<html>
<head>
<meta http-equiv = "content-type" content = "text/html; charset = utf-8">
<title> ajax接続キュー</title>
<スクリプトsrc = "utils.js"> </script>
<スクリプトsrc = "queue.js"> </script>
<script type = "text/javascript">
AddEvent(window、 'load'、function(){
// 成し遂げる。
var q = new ded.queue;
Q.SetTretryCount(5);
Q.Settimeout(3000);
var items = $( 'items');
var results = $( 'results');
var queue = $( 'queue-items');
//クライアントのリクエストを追跡します
var requests = [];
//フラッシュの各リクエストの後、特別な処理手順を購読する
Q.onflush.subscribe(function(data){
results.innerhtml = data;
requests.shift();
queue.innerhtml = requests.toString();
});
//サブスクリプション時間処理手順
Q.onfailure.subscribe(function(){
results.innerhtml += '<span style = "color:red;">接続エラー!</span>';
});
//すべての成功した処理手順xを購読します
Q.oncomplete.subscribe(function(){
results.innerhtml += '<span style = "color;">完了!</span>';
});
var actiondispatcher = function(element){
switch(element){
ケース「フラッシュ」:
Q.Flush();
壊す;
ケース「dequeue」:
q.dequeue();
requests.pop();
queue.innerhtml = requests.toString();
壊す;
ケース「一時停止」:
Q.Pause();
壊す;
ケース「クリア」:
Q.CLEAR();
リクエスト= [];
queue.innerhtml = '';
壊す;
}
};
var addRequest = function(request){
var data = request.split( ' - ')[1];
Q.Add({
方法:「取得」、
URI: 'Bridge-Connection-Queue.php?ajax = true&s =' + data、
パラメーション:null
});
requests.push(data);
queue.innerhtml = requests.toString();
};
AddEvent(items、 'click'、function(e){
var e = e || window.event;
var src = e.target || E.SRCELEMENT;
試す {
E.PreventDefault();
}
catch(ex){
e.ReturnValue = false;
}
ActionDispatcher(src.id);
});
var adders = $( 'adders');
addevent(adders、 'click'、function(e){
var e = e || window.event;
var src = e.target || E.SRCELEMENT;
試す {
E.PreventDefault();
}
catch(ex){
e.ReturnValue = false;
}
addRequest(src.id);
});
});
</script>
<style type = "text/css" media = "screen">
体
{
フォント:100%ジョージア、タイムズ、セリフ。
}
H1、H2
{
font-weight:正常;
}
#Queue-Items
{
高さ:1.5EM;
}
#追加
{
パディング:.5em;
背景:#ddd;
国境:1pxソリッド#bbb;
}
#結果領域
{
パディング:.5em;
国境:1pxソリッド#bbb;
}
</style>
</head>
<body id = "example">
<div id = "doc">
<h1>
非同期結合リクエスト</h1>
<div id = "queue-items">
</div>
<div id = "add-stuff">
<h2>キューに新しいリクエストを追加</h2>
<ul id = "adders">
<li> <a href = "#" id = "action-01"> "01"をキューに追加</a> </li>
<li> <a href = "#" id = "action-02"> "02"をキューに追加</a> </li>
<li> <a href = "#" id = "action-03"> "03"をキューに追加</a> </li>
</ul>
</div>
<h2> Quote Control </h2>
<ul id = 'アイテム'>
<li> <a href = "#" id = "フラッシュ">フラッシュ</a> </li>
<li> <a href = "#" id = "dequeue"> dequeue </a> </li>
<li> <a href = "#" id = "Pause"> Pause </a> </li>
<li> <a href = "#" id = "clear">クリアクリア</a> </li>
</ul>
<div id = "results-area">
<h2>
結果:
</h2>
<div id = "results">
</div>
</div>
</div>
</body>
</html>
この例では、フラッシュキュー、キューの一時停止、キューのリクエストの削除、クリアキューなどのさまざまなアクションを実行できます。同時に、誰もが橋の力を経験したと思います。
要約します
ブリッジモードの利点も明らかです。いくつかの主な利点のみをリストします。
1.インターフェイスと実装の部分を分離します。実装が常にインターフェイスにバインドされない場合があります。抽象クラス(関数)の実装は、実行時に構成でき、オブジェクトは実行時に実装を変更することもできます。また、抽象化と実装を完全に切り離します。これは、レイヤー化にも役立つため、より良い構造化されたシステムが生成されます。
2。スケーラビリティを改善します
3.実装の詳細は顧客に対して透明であり、顧客からの実装の詳細を隠すことができます。
同時に、ブリッジモードには独自の欠点もあります。
多数のクラスが開発コストの増加につながり、パフォーマンスも削減される可能性があります。