推薦システムをCで作成する

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
Sera
記事: 31
登録日時: 10年前

推薦システムをCで作成する

#1

投稿記事 by Sera » 10年前

Webで推薦システム(協調フィルタリング)を実装してみたいと思ったのですが、
参考文献などを見てみると、Pythonについての文献しか出てこなかったのでここで質問します。
ピアソンの積率相関係数など、必要最低限の勉強はしています。
http://gihyo.jp/dev/serial/01/informati ... ystem/0005
こちらのサイトを参考に勉強しています。
その中の協調フィルタリングについてが良く理解できません。
Userとitemの部分についてのコードを説明していただけるとありがたいです。
下はソースコードです

コード:

#! /usr/local/bin/python
# -*- coding:utf-8 -*-

import sys


def jaccard(v1, v2):
    """
    jacard係数を求める
    """
    v1_and_v2 = 0.
    v1_or_v2 = 0.
    for i in xrange(len(v1)):
        if v1[i] == 1 or v2[i] == 1:
            v1_or_v2 += 1
            if v1[i] == 1 and v2[i] == 1:
                v1_and_v2 += 1
    try:
        return v1_and_v2 / v1_or_v2
    except ZeroDivisionError:
        return 0.0


def calc_users_similarity(user_id, user_data, sim=jaccard):
    """
    userとuserの類似度を求める
    """
    users_similarity = {}
    for target_id in xrange(len(user_data)):
        if target_id == user_id:
            continue
        users_similarity[target_id] = sim(
            user_data[user_id], user_data[target_id])
    return users_similarity


def calc_user_average_score(user_id, user_data):
    """
    ユーザーの平均スコア
    """
    return sum(user_data[user_id]) / len(user_data[user_id])


def userbase_scoring(user_id, item_id, user_data, users_similarity):
    """
    userとitemのスコアを求める
    """
    if user_data[user_id][item_id] == 1.:
        return -1. * sys.maxint
    ave_score = calc_user_average_score(user_id, user_data)
    bunshi = 0.
    bunbo = 0.
    for target_id in xrange(len(user_data)):
        if target_id == user_id:
            continue
        bunshi += users_similarity[target_id] * (
            user_data[target_id][item_id]
            - calc_user_average_score(target_id, user_data)
        )
        bunbo += users_similarity[target_id]

    return ave_score + (bunshi/bunbo)


if __name__ == "__main__":
    user_data = [[1., 0., 1., 0.],
                 [1., 0., 0., 1.],
                 [1., 1., 1., 0.],
                 [0., 1., 0., 0.]]
    user_id = int(sys.argv[1])
    users_similarity = calc_users_similarity(user_id, user_data, sim=jaccard)
    for item_id in xrange(len(user_data[0])):
        print "item{}:".format(item_id),
        print userbase_scoring(user_id, item_id, user_data, users_similarity)

beatle
記事: 1281
登録日時: 12年前
住所: 埼玉
連絡を取る:

Re: 推薦システムをCで作成する

#2

投稿記事 by beatle » 10年前

「Userとitemの部分」とはuserbase_scoring関数の中身ということですか?
また、どのレベルの説明が欲しいですか?
  • Pythonコードが読めないので、一行一行のPythonコードを日本語で説明して欲しい
  • Pythonコードは分かるが、全体的に何やってるか分からない

Sera
記事: 31
登録日時: 10年前

Re: 推薦システムをCで作成する

#3

投稿記事 by Sera » 10年前

beatle さんが書きました:「Userとitemの部分」とはuserbase_scoring関数の中身ということですか?
また、どのレベルの説明が欲しいですか?
  • Pythonコードが読めないので、一行一行のPythonコードを日本語で説明して欲しい
  • Pythonコードは分かるが、全体的に何やってるか分からない
返信がおくれてすみません。
Python自体が初心者同然なものなので、一行一行恐縮ですが日本語で説明していただけたら幸いです

beatle
記事: 1281
登録日時: 12年前
住所: 埼玉
連絡を取る:

Re: 推薦システムをCで作成する

#4

投稿記事 by beatle » 10年前

各行の動作をコメントで書き込みました。
これで分かりますか?

コード:

def userbase_scoring(user_id, item_id, user_data, users_similarity):
    """
    userとitemのスコアを求める
    """
    # item_idが1.0のユーザだったら
    if user_data[user_id][item_id] == 1.:
        # -1.0 × sys.maxint を返す
        return -1. * sys.maxint
    # user_idとuser_dataを引数にしてcalc_user_average_scoreを呼び出し、戻り値をave_scoreに代入する
    ave_score = calc_user_average_score(user_id, user_data)
    # bunshi, bunboに0.0を代入する
    bunshi = 0.
    bunbo = 0.
    # target_idを[0, 1, 2, ..., len(user_data)-1]で繰り返す
    # 繰り返すたび、target_id変数に0, 1, 2, ..., len(user_data)-1の整数が順番に入ります
    for target_id in xrange(len(user_data)):
        # target_idとuser_idが等しいとき
        if target_id == user_id:
            # for先頭に戻る(以下の計算はtarget_id≠user_idを仮定しているということ)
            continue
        # bunshiに計算結果を加える
        bunshi += users_similarity[target_id] * (
            user_data[target_id][item_id]
            - calc_user_average_score(target_id, user_data)
        )
        # bunboにusers_similarity[target_id]の値を加える
        bunbo += users_similarity[target_id]
 
    # 計算結果を返す
    return ave_score + (bunshi/bunbo)

Sera
記事: 31
登録日時: 10年前

Re: 推薦システムをCで作成する

#5

投稿記事 by Sera » 10年前

beatle さんが書きました:各行の動作をコメントで書き込みました。
これで分かりますか?

コード:

def userbase_scoring(user_id, item_id, user_data, users_similarity):
    """
    userとitemのスコアを求める
    """
    # item_idが1.0のユーザだったら
    if user_data[user_id][item_id] == 1.:
        # -1.0 × sys.maxint を返す
        return -1. * sys.maxint
    # user_idとuser_dataを引数にしてcalc_user_average_scoreを呼び出し、戻り値をave_scoreに代入する
    ave_score = calc_user_average_score(user_id, user_data)
    # bunshi, bunboに0.0を代入する
    bunshi = 0.
    bunbo = 0.
    # target_idを[0, 1, 2, ..., len(user_data)-1]で繰り返す
    # 繰り返すたび、target_id変数に0, 1, 2, ..., len(user_data)-1の整数が順番に入ります
    for target_id in xrange(len(user_data)):
        # target_idとuser_idが等しいとき
        if target_id == user_id:
            # for先頭に戻る(以下の計算はtarget_id≠user_idを仮定しているということ)
            continue
        # bunshiに計算結果を加える
        bunshi += users_similarity[target_id] * (
            user_data[target_id][item_id]
            - calc_user_average_score(target_id, user_data)
        )
        # bunboにusers_similarity[target_id]の値を加える
        bunbo += users_similarity[target_id]
 
    # 計算結果を返す
    return ave_score + (bunshi/bunbo)
なるほど!Pythonについての参考サイトがあまり見当たらなかったのでとても役立ちました!
今後も解答をいただけたら幸いです!

閉鎖

“C言語何でも質問掲示板” へ戻る