2012年7月4日 星期三

[JavaScript] Observer Pattern Implement

上一篇講到簡單的observer Pattern的作法,這一篇我們把它寫成一個class
//Observer class
function Observer() {
  var topics = [];
   
   return{
    Register:function( topic, func ) {
        if(!topics[topic])
         topics[topic]=[]; // two dimension for store callback func
        topics[topic].push(func);
    },
    
    Publish:function( topic, args ) {
        if ( !topics[topic] ) {
            console.log('no such topic');
            return false;
        }
        var subscribers = topics[topic];
        for(var i in subscribers)
         subscribers[i](topic,args);
    },
    
    UnRegister:function( topic ) {
        if ( !topics[topic] ) {
            return false;
        }
        topics[topic]=null;
    }
   }
};
如何使用呢?
//How to use
var observ = new  Observer();
 
 //call back signature (topic,data)
 var testHandler = function (topics, data) {
    console.log("1:"+topics + ": " + data);
 };
 var testHandler2 = function (topics, data) {
    console.log("2:"+topics + ": " + data);
 };
 
 observ.Register('cal1', testHandler);
 observ.Register('cal1', testHandler2);
 observ.Publish('cal1', 'hello world!');
 observ.Publish('cal1', ['test', 'a', 'b', 'c']);
 
 observ.UnRegister('example1');
 
 observ.Publish('example1', 'hello world!');

------------------
執行結果如下


沒想到使用Javascript寫一個Observer Pattern會如此簡單 ....

2012年7月2日 星期一

[JavaScript] Observer Pattern Cont.

續上篇
Observer Pattern真的是一個蠻好用的Pattern,以我工作的例子是我會去操作一個第三方的JavaScript API,操作完之後這個API只會產生一個事件,而且這個事件裡面會帶一個參數表示目前的狀態
如下
trdParty.onCallback(function(status){
   // do something you want
});

trdParty.doMethod();

onCallback會在每次呼叫不同的doMethod都會回傳目前的狀態,你可以透過偵測status的狀態來執行你想做的事情,最簡單的方式是透過類似HashTable的方式來做mapping,如下
var funMap = [];
funMap['status1'] = function(status)
{
   //do statu1 need to do
};
funMap['status2'] = function(status)
{
   //do statu2 need to do
};

trdParty.onCallback(function(status){
   funMap[status.Text](status); //這裡就會依照status.Text的狀態類型呼叫對應的method了
});

trdParty.doMethod();
透過以上的方法可以簡單的做funciton mapping呼叫。但如果針對一個status可能有好幾件事情要做呢?
說真的,透過JavaScript來達到二維的呼叫也是很簡單
var funMap = [][]; //二維
funMap['status1'].push(function(status)
{
   //do statu1 need to do -- 1
});
funMap['status1'].push(function(status)
{
   //do statu1 need to do -- 2
});
funMap['status2'].push(function(status)
{
   //do statu2 need to do -- 1
});
funMap['status2'].push(function(status)
{
   //do statu2 need to do -- 2
});

trdParty.onCallback(function(status){
   for(var fn in funMap[status.Text])
   {
      funMap[status.Text][fn](status);
   }
});

trdParty.doMethod();

怎樣,很簡單吧。

不過這樣寫每次沒辦法利用,時間晚了,下次再來介紹整個Observer Pattern...

2012年6月28日 星期四

[JavaScript] Observer Pattern

這是在我日常的工作中是一個很常被使用到的Pattern,它使用起來的方式如下
var callback = function(topic, data){
   console.log(topic + ': ' + data);
}

//假設observe object 已存在
observe.addCallback('MyTopic',callback);

observe.fireCallback('Mytopic', 'my data 1');  // Mytopic : my data 1
observe.fireCallback('Mytopic', 'my data 2');  // Mytopic : my data 2
observe.fireCallback('Mytopic', 'my data 3');  // Mytopic : my data 3


基本上使用起來很像.NET中event的方式

To be continue ...

[JavaScript] Advanced Object Declaration

上一篇文章中提到了幾個JavaScript class的宣告方式,以及用該class來宣告物件。而這一篇會介紹比較Advanced的物件宣告方式

Literal
//object declaration with attribute and method
var person = {
 //public attribute
 name:'',
 year:0,
 
 //public function
 Init:function(name, year){
  this.name=name;
  this.year=year; 
 }
}

Module
//can declare private/public attribte and method
var Person = (function(){
 //private attribute
 var name;
 
 var privateInfo=function(){
  return this.name;
 };
 
 //All public method and attribute
 return{
  //public attribute
  Nickname:'Andy',
  //public method
  getInfo:function(){
   return Nickname + " - " + name;    
  }
 }
})();

目前看起來好像只有透過所謂Module的宣告方式才可以有public/private的特性,其他方式的的宣告方法看起來都沒有這個效果.

有鑑於有我第一次看到Module的宣告方式看了好久都看不懂,還以為是所謂的新語法,其實不是,帶我一一來拆解
//一般方法的宣告方式
var Person = function(){ /*do what you want*/ };

//execute method
Person();

//如果方法裡面有回傳值
var Person = function(){ 
 /*do what you want*/ 
 
 // return a JSON object
 return{
  pubVar:'',
  pubMethod:function()
  {
   // do method
  }
  
   
 }
};
//execute the same method
var obj = Person();
//get PubVar
var val = obj.pubVar;
//execute pubmethod
obj.pubMethod();
那如果宣告的同時就順便執行呢?
//用()把整個function的宣告包起來後順便再()執行
var person = (function(){ /*do what you want */ })();

//get PubVar
var val = obj.pubVar;
//execute pubmethod
obj.pubMethod();


不曉得各位看官有沒有看懂了

2012年6月20日 星期三

JavaScript class 宣告方式

在JavaScript的語法中,光是class的宣告方式就有好幾種,底下列出我所知道的宣告方式

function Person(name,year){
 //public attribute
 this.name=name;
 this.year=year;
 
 //public method
 this.getInfo(){
  return 'I am '+ this.name + 
      ',and I am ' + this.year + 'years old';
 }
}

用法
var p = new Person('Andy','18');
p.getInfo();

你也可以透過Prototype的方式宣告
function Person(name,year){
 //public property
 this.name=name;
 this.year=year;
}
//public method
//底下方法也可以宣告public property
//public method
Person.prototype.getInfo = function(){
  //public method
  return 'I am '+ this.name + 
      ',and I am ' + this.year + 'years old';
};
..
或者這樣宣告
var Person = function(name,year){
 //public attribute
 this.name=name;
 this.year=year;
};

//public method
Person.prototype.getInfo = function(){
  //public method
  return 'I am '+ this.name + 
      ',and I am ' + this.year + 'years old';
};
另一種宣告class的方法,不過這個方法我不知道怎麼宣告constructor
var Person = new Class;

//public method
Person.prototype.getInfo = function(){
  //public method
  return 'I am '+ this.name + 
      ',and I am ' + this.year + 'years old';
};

靜態方法(static method)部分,可以這樣宣告

//Person is class name
Person.find = function(id){/* ... */}


//instance method部分,也可以這樣宣告

//instance a Person object
var person = new Person('Andy',18);
person.find = function(id){/*  .... */}


下次再來介紹如何宣告物件 ....

2012年3月19日 星期一

[讀書心得 part4] 交辦時,務必說清楚、想明白

大家好,我又來分享讀書心得啦 ^^
今天跟大家分享訣竅三
  1. 勉強他的能力,不要勉強他的意願
    • 話說沒有意願,能力再好都是枉然,可見意願的重要性。所以平常一定要跟member混熟,指派工作的時候,一定要了解他的能力是否有辦法完成這個交辦,如果有辦法完成自然比較好說服,如果比較難完成,那在指派的時候也一定要想辦法說服他。我很常會用的招式是:你把這件事情完成,你就會學習到以後該怎麼處理這樣類型的工作了。目前看起來成效很爛(冏)
  2. 他有沒有個人目標,會影響工作成敗
    • 說真的,我也覺得這點很重要,但問題要讓member有個人目標其實真的還蠻難的,我也曾經幫member訂過目標,但效果其實不符合預期,或許我該找時間好好來跟member談談他的目標到底在哪?
  3. 不合理的工作要求,交辦給誰最好呢?
    • 我覺得交辦給誰都不好,所以如果可以把不合理的工作要求合理化,那交辦出去的機會可能會大一點。例如寫程式,一隻程式可以花一天沒架構沒規劃的方式寫出來,也可以花三天好好的規畫寫出來,當時間急的時候,你要一個很有sense的member花一天寫出來,你該如何說服他?去年我就常遇到這樣的事情。那時候跟我合作的member能力非常好,但對程式撰寫有一定程度的潔癖,說真的,要我寫出一個很糟的程式,對我來說也是一種虐待。所以我會先跟他討論,跟他說目前事情的急迫性,以及目前會跟老闆報告說現在的方式會產生的問題,日後我們需要再額外花時間來refactor目前寫的程式,讓老闆知道。還好那位member跟我交情還不錯,我們就這樣完成了大多數的程式,之後有被refactor的部分也有80%以上。
    • 所以我寧願先讓事情盡量合理化,再來做所謂的交辦,萬一不行,也跟member討論出平衡點。
  4. 他不是你的分身,做法不一樣,千萬別跳腳
    • 話說寫程式裡有一個流程叫做code review,通常是組織裡比較資深的member幫比較資淺的member review code,review的過程中,可以提出建議的做法,以及指出有問題的地方。我覺得code review 對我來說也是練功的一種,有時候可以看到自己沒想過的作法,當然有時候也會看到讓自己氣得跳腳的寫法。從寫程式就可以知道,針對同一種需求,不同的人去寫程式,通常不太可能寫出一樣的code,但只要知道目標在哪(這真的很重要),確定過程中都是往目標的正確路徑,我想就算中間稍微停頓看個風景也不為過。

2012年3月12日 星期一

[讀書心得 part3] 硬塞前,先慎選人與事

今天來跟大家分享【交辦的技術 讀書心得 Part3】


  1. 交辦標準,不是看他做不做得到
    • 作者說交辦是指把這件事情的【責任】交付出去給member,member在接到工作的同時也同時擔負起完成這件事情的【責任】。身為Leader腦袋真的要轉過來,雖然明明知道很多事情member其實並沒有足夠的能力來完成,但如果一昧的攬在自己的身上,到頭來只是讓自己更累,團隊產出更少,而且少了培養member的機會,會讓整個團隊的競爭力降低。
    • 當member承擔這個任務成敗的【責任】後,勢必會更用心的去處理,過程中千萬別插手,一插手,事情的責任馬上就轉到自己身上了。例如,你叫member寫一個專案Deploy的SOP,過程中如果你插手給予意見,則member勢必認為只要把你的意見加入,就萬無一失,有問題的話也不是自己的問題,因為已經參照你給的意見來執行了,所以身為Leader千萬要忍住。
    • 當然還是要評估這件事情是不適合由該member來執行,如果難度太高,一樣會陷入【交辦失敗】的魔咒,所以身為Leader可能還是需要想一些方式讓Member可以較順利的執行該任務,藉由完成該任務來提升member的能力。
  2. 三種工作,別突然硬塞
    1. 陌生的工作
    2. 非緊急重要事項
    3. 指派人力的工作
    • 針對上述三項工作,我覺得比較有趣的是【非緊急重要事項】。前陣子剛好看了某時間管理的文章,文中將事情分為四個象限,分別是【緊急】、【重要】、【非緊急】、【非重要】。將這四個象限去組合,則可以得到【非緊急重要事項】。而處理這四個現象的先後順序分別是1.【緊急重要】2.【非緊急重要】3.【緊急非重要】4.【非緊急非重要】。很多人常常把2,3處理搞混,連我都不例外,不過只要接受這個理論,就可以順利地交辦的事項一一完成。
    • 所謂【非緊急重要事項】通常是長久規畫的策略或方針,將這類的事情交辦給部屬,無疑是主管自己無能(機會高),或者真的是member能力超好(機會低)。member對於due date還很久的事項,通常較缺乏經驗去執行,而且這類的事物通常有很多事情並非member的權責可以決定,例如:半年後的新專案開發架構。身為Leader必須將這類事務細分成多個工作包(WBS),當細分成WBS後,即可讓每個WBS依序成為【緊急重要事項】,則member依WBS的順序去執行,則每個階段就都可以有產出,最後完成這個【非緊急重要事項】。
    • 至於另外兩個【 陌生的工作 】和【 指派人力的工作 】接導因於member對這類交辦經驗薄弱,例如 指派人力的工作,member可能連自己要完成某個交辦需花多少時間都估不出來了,你還要他去指派別人工作? 
  3. 預防災難,你得會看人
    • 其實這個部份我還很少機會用到,書上指的是要會用【領導人】,小弟我還沒機會成為可以指派【領導人】的人。不過重點還是開船著船長要知道目的地在哪,路線規劃要漂亮,相關環境變數收集齊全,才能順利帶領船員,快快樂樂的出航,平平安安且順順利利的到達目的地。
  4. 菜鳥和老鳥,交辦方式肯定不一樣
    • 這應該是廢話,但不知道會不會有人白目到連這個都不知道。不過菜鳥分兩種【能力好的】跟【能力差的】;老鳥也分兩種【能力好的】和【能力差的】。針對菜鳥當然再交辦事項的時候要給予適當的指導,但遇到能力好的,更需要給予適當的發揮及尊重,這是我個人的感覺。而老鳥部分,能力好的就給予極度的尊重,但別忘了還是要訂一下schedule,能力差的我會跟他討論,並希望盡量藉由討論來取得他願意執行的平衡點,重點還是schedule要訂一下,不然滑掉的機會很高。