3章 その5 ピアソン相関距離の計算

2章で実装した
http://d.hatena.ne.jp/shokai/20081004/1223126485
とは別に作る。


p.38より
ピアソン相関距離を計算する関数をclusters.rbに追加

http://www.bitbucket.org/shokai/collective-intelligence-study/src/82884830d372/03/clusters.rb

  # ピアソン相関距離を計算
  def pearson(v1,v2)
    # 単純な合計
    sum1 = 0
    v1.each{ |n|
      sum1 += n
    }
    sum2 = 0
    v2.each{ |n|
      sum2 += n
    }
    
    # 平方の合計
    sum1Sq = 0
    v1.each{ |n|
      sum1Sq += n*n
    }
    sum2Sq = 0
    v2.each{ |n|
      sum2Sq += n*n
    }
    
    # 積の合計
    pSum = 0
    for i in 0..v1.length-1
      pSum += v1[i]*v2[i]
    end
    
    # ピアソンによるスコアを算出
    num = pSum - (sum1*sum2/v1.length)
    den = Math::sqrt( (sum1Sq-sum1*sum1/v1.length)*(sum2Sq-sum2*sum2/v1.length) )
    return 0 if den == 0
    
    # 今回は特別に、アイテム同士が似ているほど小さい値を返す様にする
    return 1.0-num/den


irbで試す

>> require 'clusters.rb'
=> true
>> cs = Clusters.new
=> #<Clusters:0x69abcc>
>> cs.pearson([1,2,3], [1,2,3])
=> 0.0
>> cs.pearson([1,2,3], [1,2,5])
=> 0.0571909584179365