2014-01-11 13 views
5

私はムービー上のユーザーから与えられたレーティングに対してnumpy配列を持っています。評価は1と5の間で行われ、0はユーザーが映画を評価しないことを意味します。各映画の平均視聴率と各ユーザーの平均視聴率を計算したいと思います。言い換えれば、私は非ゼロ要素の各列または行の平均を計算します。非ゼロ要素の各列または行の平均を計算するための効率的な方法

このケースを処理する効率的なnumpy配列関数はありますか?列や行による評価を手動で繰り返すことで問題を解決できます。

ありがとうございます!

+1

アレイはどのように整理されていますか?配列をロードする方法のコードサンプルを与えることができますか?ファイルから読み込む場合は、ファイル形式のサンプルも投稿してください。 – Keeler

+0

@GarudaReigaという回答を受け入れることを忘れないでください。 – MERose

答えて

7

廃棄する値は0であるので、あなたは軸に沿って合計を実行した後(同じ軸に沿って)非ゼロ要素の数で割ることによって手動で平均を計算することができる:

a = np.array([[8.,9,7,0], [0,0,5,6]]) 
a.sum(1)/(a != 0).sum(1) 

結果を表示されるように、0は平均では考慮されません。

5

0の値をすべてnp.nanに変換した後に、np.nanmeanを使用できます。 np.nanmeannumpy 1.8でのみご利用いただけます。

import numpy as np 

ratings = np.array([[1,4,5,0], 
        [2,0,3,0], 
        [4,0,0,0]], dtype=np.float) 


def get_means(ratings): 
    ratings[np.where(ratings == 0)] = np.nan 

    user_means = np.nanmean(ratings, axis=1) 
    movie_means = np.nanmean(ratings, axis=0) 

    return {'user_means' : user_means, 'movie_means' : movie_means} 

結果:

>>> get_means(ratings) 
{'movie_means': array([ 2.33333333, 4.  , 4.  ,   nan]), 

'user_means': array([ 3.33333333, 2.5  , 4.  ])} 
+1

1.8でnummeに 'nanmean'が追加されましたが、' scipy.stats'にかなりのバージョンがあります。 –

2

別の代替法は、マスク0値で、マスクされた配列を使用することです。例えば(Akavaliのサンプルデータ@使用):

In [30]: ratings = np.array([[1,4,5,0], 
    ....:      [2,0,3,0], 
    ....:      [4,0,0,0]], dtype=np.float) 

マスクとしてratings==0を使用して、ratingsのマスクされたバージョンを作成します。

In [31]: mratings = np.ma.masked_array(ratings, mask=ratings==0) 

In [32]: mratings 
Out[32]: 
masked_array(data = 
[[1.0 4.0 5.0 --] 
[2.0 -- 3.0 --] 
[4.0 -- -- --]], 
      mask = 
[[False False False True] 
[False True False True] 
[False True True True]], 
     fill_value = 1e+20) 

今、各軸に沿って平均値を計算する:

In [33]: mratings.mean(axis=0) 
Out[33]: 
masked_array(data = [2.3333333333333335 4.0 4.0 --], 
      mask = [False False False True], 
     fill_value = 1e+20) 

In [34]: mratings.mean(axis=1) 
Out[34]: 
masked_array(data = [3.3333333333333335 2.5 4.0], 
      mask = [False False False], 
     fill_value = 1e+20) 
関連する問題