Ejemplo n.º 1
0
class Hybrid3ScoreSubRecommender(BaseRecommender):
    """Hybrid3ScoreSubRecommender recommender"""

    RECOMMENDER_NAME = "Hybrid3ScoreRecommender"

    def __init__(self, data: DataObject):
        super(Hybrid3ScoreSubRecommender, self).__init__(data.urm_train)
        urm = sps.vstack([data.urm_train, data.icm_all_augmented.T])
        urm = urm.tocsr()
        self.slim = SLIMElasticNetRecommender(urm)
        self.rp3 = RP3betaRecommender(self.URM_train)
        self.itemcf = ItemKNNCFRecommender(self.URM_train)
        self.random_seed = data.random_seed



    def fit(self, alpha_beta_ratio=1, alpha_gamma_ratio=1):
        try:
            self.slim.load_model('stored_recommenders/slim_elastic_net/',
                                 f'with_icm_{self.random_seed}_topK=100_l1_ratio=0.04705_alpha=0.00115_positive_only=True_max_iter=35')
        except:
            self.slim.fit(topK=100, l1_ratio=0.04705, alpha=0.00115, positive_only=True, max_iter=35)
            self.slim.save_model('stored_recommenders/slim_elastic_net/',
                                 f'with_icm_{self.random_seed}_topK=100_l1_ratio=0.04705_alpha=0.00115_positive_only=True_max_iter=35')

        self.rp3.fit(topK=20, alpha=0.16, beta=0.24)
        self.itemcf.fit(topK=22, shrink=850, similarity='jaccard', feature_weighting='BM25')

        self.alpha = 1
        self.beta = alpha_beta_ratio
        self.gamma = alpha_gamma_ratio


    def _compute_item_score(self, user_id_array, items_to_compute = None):
        # ATTENTION!
        # THIS METHOD WORKS ONLY IF user_id_array IS A SCALAR AND NOT AN ARRAY
        # TODO

        scores_slim = self.slim._compute_item_score(user_id_array=user_id_array)
        scores_rp3 = self.rp3._compute_item_score(user_id_array=user_id_array)
        scores_itemcf = self.itemcf._compute_item_score(user_id_array=user_id_array)

        # normalization
        slim_max = scores_slim.max()
        rp3_max = scores_rp3.max()
        itemcf_max = scores_itemcf.max()

        if not slim_max == 0:
            scores_slim /= slim_max
        if not rp3_max == 0:
            scores_rp3 /= rp3_max
        if not itemcf_max == 0:
            scores_itemcf /= itemcf_max

        scores_total = self.alpha * scores_slim + self.beta * scores_rp3 + self.gamma * scores_itemcf

        return scores_total
class Hybrid3ScoreRecommender(BaseRecommender):
    """Hybrid3ScoreRecommender recommender"""

    RECOMMENDER_NAME = "Hybrid3ScoreRecommender"

    def __init__(self, data: DataObject, random_seed: int, alpha=1):
        super(Hybrid3ScoreRecommender, self).__init__(data.urm_train)
        self.random_seed = random_seed
        self.slim = SLIMElasticNetRecommender(self.URM_train)
        self.rp3 = RP3betaRecommender(self.URM_train)
        self.itemcf = ItemKNNCFRecommender(self.URM_train)
        self.alpha = alpha

    def fit(self, alpha_beta_ratio=1, alpha_gamma_ratio=1):

        self.slim.load_model(
            '', 'SLIM_ElasticNetURM_seed=' + str(self.random_seed) +
            '_topK=100_l1_ratio=0.04705_alpha=0.00115_positive_only=True_max_iter=35'
        )
        self.rp3.fit(topK=20, alpha=0.16, beta=0.24)
        self.itemcf.fit(topK=22,
                        shrink=850,
                        similarity='jaccard',
                        feature_weighting='BM25')

        # self.alpha = 1
        self.beta = self.alpha * alpha_beta_ratio
        self.gamma = self.alpha * alpha_gamma_ratio

    def _compute_item_score(self, user_id_array, items_to_compute=None):
        # ATTENTION!
        # THIS METHOD WORKS ONLY IF user_id_array IS A SCALAR AND NOT AN ARRAY
        # TODO

        scores_slim = self.slim._compute_item_score(
            user_id_array=user_id_array)
        scores_rp3 = self.rp3._compute_item_score(user_id_array=user_id_array)
        scores_itemcf = self.itemcf._compute_item_score(
            user_id_array=user_id_array)

        # normalization
        slim_max = scores_slim.max()
        rp3_max = scores_rp3.max()
        itemcf_max = scores_itemcf.max()

        if not slim_max == 0:
            scores_slim /= slim_max
        if not rp3_max == 0:
            scores_rp3 /= rp3_max
        if not itemcf_max == 0:
            scores_itemcf /= itemcf_max

        scores_total = self.alpha * scores_slim + self.beta * scores_rp3 + self.gamma * scores_itemcf

        return scores_total
Ejemplo n.º 3
0
class HybridScoreRecommender(BaseRecommender):
    """HybridScoreRecommender recommender"""

    RECOMMENDER_NAME = "HybridScoreRecommender"

    def __init__(self, data: DataObject, random_seed: int):
        super(HybridScoreRecommender, self).__init__(data.urm_train)
        self.random_seed = random_seed
        self.slim = SLIMElasticNetRecommender(self.URM_train)
        self.rp3 = RP3betaRecommender(self.URM_train)


    def fit(self, alpha=0.5):
        self.slim.load_model('', 'SLIM_ElasticNetURM_seed='
                             + str(self.random_seed) +
                             '_topK=100_l1_ratio=0.04705_alpha=0.00115_positive_only=True_max_iter=35')
        self.rp3.fit(topK=20, alpha=0.16, beta=0.24)
        self.alpha = alpha


    def _compute_item_score(self, user_id_array, items_to_compute = None):
        # ATTENTION!
        # THIS METHOD WORKS ONLY IF user_id_array IS A SCALAR AND NOT AN ARRAY
        # TODO

        scores_slim = self.slim._compute_item_score(user_id_array=user_id_array)
        scores_rp3 = self.rp3._compute_item_score(user_id_array=user_id_array)

        # normalization
        slim_max = scores_slim.max()
        rp3_max = scores_rp3.max()

        if not slim_max == 0:
            scores_slim /= slim_max
        if not rp3_max == 0:
            scores_rp3 /= rp3_max

        scores_total = self.alpha * scores_slim + (1 - self.alpha) * scores_rp3
        return scores_total
Ejemplo n.º 4
0
class HybridNico(BaseRecommender):
    """Hybrid100AlphaRecommender recommender"""

    RECOMMENDER_NAME = "HybridNico"

    def __init__(self, data: DataObject, random_seed: int):
        super(HybridNico, self).__init__(data.urm_train)
        self.random_seed = random_seed
        self.slim = SLIMElasticNetRecommender(self.URM_train)
        self.rp3 = RP3betaRecommender(self.URM_train)
        self.number_of_users = data.number_of_users

    def fit(self, alpha=0.5):
        self.slim.load_model(
            '', 'SLIM_ElasticNetURM_seed=' + str(self.random_seed) +
            '_topK=100_l1_ratio=0.04705_alpha=0.00115_positive_only=True_max_iter=35'
        )
        self.rp3.fit(topK=20, alpha=0.16, beta=0.24)

        path_slim = 'slim_item_scores_random_seed=' + str(self.random_seed)
        path_rp3 = 'slim_item_scores_random_seed=' + str(self.random_seed)

        # cache = (os.path.exists(path_slim + '.npy') and os.path.exists(path_rp3 + '.npy'))
        cache = False

        print("cache is hardcoded to:")
        print(cache)

        if cache:
            self.fit_cached(path_slim=path_slim,
                            path_rp3=path_rp3,
                            alpha=alpha)
        else:
            self.fit_no_cached(path_slim=path_slim,
                               path_rp3=path_rp3,
                               alpha=alpha)

    def fit_cached(self, path_slim, path_rp3, alpha=0.5):
        mat_scores_slim = np.load(path_slim + '.npy')
        mat_scores_rp3 = np.load(path_rp3 + '.npy')

        self.score_matrix = alpha * mat_scores_slim + (1 -
                                                       alpha) * mat_scores_rp3

    def fit_no_cached(self, path_slim, path_rp3, alpha=0.5):

        user_id_array = np.array(range(self.number_of_users))

        self.mat_scores_slim = self.slim._compute_item_score(
            user_id_array=user_id_array)
        self.mat_scores_rp3 = self.rp3._compute_item_score(
            user_id_array=user_id_array)

        # normalization
        self.mat_scores_slim /= self.mat_scores_slim.max()
        self.mat_scores_rp3 /= self.mat_scores_rp3.max()

        # np.save(path_slim, arr=mat_scores_slim)
        # np.save(path_rp3, arr=mat_scores_rp3)

        self.score_matrix = alpha * self.mat_scores_slim + (
            1 - alpha) * self.mat_scores_rp3

    def _compute_item_score(self, user_id_array, items_to_compute=None):
        return self.score_matrix[user_id_array]
Ejemplo n.º 5
0
class Hybrid3ScoreRecommender(BaseRecommender):
    """Hybrid3ScoreRecommender recommender"""

    RECOMMENDER_NAME = "Hybrid3ScoreRecommender"

    def __init__(self, data: DataObject, random_seed: int, alpha=1):
        super(Hybrid3ScoreRecommender, self).__init__(data.urm_train)
        self.random_seed = random_seed
        urm = sps.vstack([data.urm_train, data.icm_all_augmented.T])
        urm = urm.tocsr()
        self.slim = SLIMElasticNetRecommender(urm)
        self.rp3 = RP3betaRecommender(urm)
        self.alpha = alpha

    def fit(self, alpha_beta_ratio=1, alpha_gamma_ratio=1):
        try:
            self.slim.load_model(
                'stored_recommenders/slim_elastic_net/',
                f'with_icm_{self.random_seed}_topK=191_l1_ratio=0.0458089_alpha=0.000707_positive_only=True_max_iter=100'
            )
        except:
            self.slim.fit(topK=191,
                          l1_ratio=0.0458089,
                          alpha=0.000707,
                          positive_only=True,
                          max_iter=100)
            self.slim.save_model(
                'stored_recommenders/slim_elastic_net/',
                f'with_icm_{self.random_seed}_topK=191_l1_ratio=0.0458089_alpha=0.000707_positive_only=True_max_iter=100'
            )
        try:
            self.rp3.load_model(
                'stored_recommenders/rp3_beta/',
                f'with_icm_{self.random_seed}_topK=40_alpha=0.4_beta=0.2')
        except:
            self.rp3.fit(topK=40, alpha=0.4, beta=0.2)
            self.rp3.save_model(
                'stored_recommenders/rp3_beta/',
                f'with_icm_{self.random_seed}_topK=40_alpha=0.4_beta=0.2')

        # self.alpha = 1
        self.beta = self.alpha * alpha_beta_ratio
        self.gamma = self.alpha * alpha_gamma_ratio

    def _compute_item_score(self, user_id_array, items_to_compute=None):
        # ATTENTION!
        # THIS METHOD WORKS ONLY IF user_id_array IS A SCALAR AND NOT AN ARRAY
        # TODO

        scores_slim = self.slim._compute_item_score(
            user_id_array=user_id_array)
        scores_rp3 = self.rp3._compute_item_score(user_id_array=user_id_array)

        # normalization
        slim_max = scores_slim.max()
        rp3_max = scores_rp3.max()

        if not slim_max == 0:
            scores_slim /= slim_max
        if not rp3_max == 0:
            scores_rp3 /= rp3_max

        scores_total = self.alpha * scores_slim + self.beta * scores_rp3

        return scores_total
Ejemplo n.º 6
0
class LinearHybrid001(BaseItemSimilarityMatrixRecommender):
    RECOMMENDER_NAME = "LinearHybrid001"

    # set the seed equal to the one of the parameter search!!!!
    def __init__(self, URM_train, ICM_train, submission=False, verbose=True, seed=1205):
        super(LinearHybrid001, self).__init__(URM_train, verbose = verbose)
        self.URM_train = URM_train
        self.ICM_train = ICM_train

        self.__rec1 = SLIMElasticNetRecommender(URM_train, verbose=False)
        self.__rec1_params = {'topK': 120, 'l1_ratio': 1e-5, 'alpha': 0.066}

        # seed 1205: 'topK': 620, 'shrink': 121, 'similarity': 'asymmetric', 'normalize': True, 'asymmetric_alpha': 0.5526988987666924
        self.__rec2 = ItemKNNCFRecommender(URM_train, verbose=False)
        self.__rec2_params = {'topK': 620, 'shrink': 121, 'similarity': 'asymmetric', 'normalize': True, 'asymmetric_alpha': 0.5526988987666924}

        # seed 1205: 'topK': 115, 'shrink': 1000, 'similarity': 'cosine', 'normalize': True, 'feature_weighting': 'BM25'
        self.__rec3 = ItemKNNCBFRecommender(URM_train, ICM_train, verbose=False)
        self.__rec3_params = {'topK': 115, 'shrink': 1000, 'similarity': 'cosine', 'normalize': True, 'feature_weighting': 'BM25'}

        self.__a = self.__b = self.__c = None
        self.seed=seed
        self.__submission=submission

    def fit(self, alpha=0.5, l1_ratio=0.5):
        self.__a = alpha * l1_ratio
        self.__b = alpha - self.__a
        self.__c = 1 - self.__a - self.__b
        if not self.__submission:
            try:
                self.__rec1.load_model('stored_recommenders/'+self.__rec1.RECOMMENDER_NAME+'/', f'seed_{str(self.seed)}_best_for_LinearHybrid001')
                print(f"{self.__rec1.RECOMMENDER_NAME} loaded.")
            except:
                print(f"Fitting {self.__rec1.RECOMMENDER_NAME} ...")
                self.__rec1.fit(**self.__rec1_params)
                print(f"done.")
                self.__rec1.save_model('stored_recommenders/'+self.__rec1.RECOMMENDER_NAME+'/', f'seed_{str(self.seed)}_best_for_LinearHybrid001')

            try:
                self.__rec2.load_model('stored_recommenders/'+self.__rec2.RECOMMENDER_NAME+'/', f'seed_{str(self.seed)}_best_for_LinearHybrid001')
                print(f"{self.__rec2.RECOMMENDER_NAME} loaded.")
            except:
                print(f"Fitting {self.__rec2.RECOMMENDER_NAME} ...")
                self.__rec2.fit(**self.__rec2_params)
                print(f"done.")
                self.__rec2.save_model('stored_recommenders/'+self.__rec2.RECOMMENDER_NAME+'/', f'seed_{str(self.seed)}_best_for_LinearHybrid001')

            try:
                self.__rec3.load_model('stored_recommenders/'+self.__rec3.RECOMMENDER_NAME+'/', f'seed_{str(self.seed)}_best_for_LinearHybrid001')
                print(f"{self.__rec3.RECOMMENDER_NAME} loaded.")
            except:
                print(f"Fitting {self.__rec3.RECOMMENDER_NAME} ...")
                self.__rec3.fit(**self.__rec3_params)
                print(f"done.")
                self.__rec3.save_model('stored_recommenders/'+self.__rec3.RECOMMENDER_NAME+'/', f'seed_{str(self.seed)}_best_for_LinearHybrid001')
        else:
            self.__rec1.fit(**self.__rec1_params)
            self.__rec2.fit(**self.__rec2_params)
            self.__rec3.fit(**self.__rec3_params)

    def _compute_item_score(self, user_id_array, items_to_compute=None):

        item_weights_1 = self.__rec1._compute_item_score(user_id_array)
        item_weights_2 = self.__rec2._compute_item_score(user_id_array)
        item_weights_3 = self.__rec3._compute_item_score(user_id_array)

        item_weights = item_weights_1 * self.__a + item_weights_2 * self.__b + item_weights_3 * self.__c

        return item_weights

    def save_model(self, folder_path, file_name = None):
        if file_name is None:
            file_name = self.RECOMMENDER_NAME

        self._print("Saving model in file '{}'".format(folder_path + file_name))
        dataIO = DataIO(folder_path=folder_path)
        dataIO.save_data(file_name=file_name, data_dict_to_save = {})
        self._print("Saving complete")
class HybridNicoSubmission(BaseRecommender):
    """HybridNicoSubmission recommender"""

    RECOMMENDER_NAME = "HybridNicoSubmission"

    def __init__(self, data: DataObject):
        super(HybridNicoSubmission, self).__init__(data.urm_train)
        self.data = data
        self.slim = SLIMElasticNetRecommender(data.urm)
        self.rp3 = RP3betaRecommender(data.urm)

    def fit(self, alpha=0.5):
        self.slim.load_model(
            '',
            'SLIM_ElasticNetFULL_URM_topK=100_l1_ratio=0.04705_alpha=0.00115_positive_only=True_max_iter=35'
        )
        self.rp3.fit(topK=20, alpha=0.16, beta=0.24)

        self.fit_no_cached(path_slim=None, path_rp3=None, alpha=alpha)

    def fit_cached(self, path_slim, path_rp3, alpha=0.5):
        mat_scores_slim = np.load(path_slim + '.npy')
        mat_scores_rp3 = np.load(path_rp3 + '.npy')

        self.score_matrix = alpha * mat_scores_slim + (1 -
                                                       alpha) * mat_scores_rp3

    def fit_no_cached(self, path_slim, path_rp3, alpha=0.5):

        n_users = self.data.number_of_users
        n_item = self.data.number_of_items
        list_slim = []
        list_rp3 = []
        for u_id in range(n_users):
            # if u_id % 1000 == 0:
            #     print('user: {} / {}'.format(u_id, n_users - 1))
            list_slim.append(
                np.squeeze(self.slim._compute_item_score(user_id_array=u_id)))
            list_rp3.append(
                np.squeeze(self.rp3._compute_item_score(user_id_array=u_id)))

        mat_scores_slim = np.stack(list_slim, axis=0)
        mat_scores_rp3 = np.stack(list_rp3, axis=0)
        '''print("slim scores stats:")
        print("min = {}".format(mat_scores_slim.min()))
        print("max = {}".format(mat_scores_slim.max()))
        print("average = {}".format(mat_scores_slim.mean()))


        print("rp3 scores stats:")
        print("min = {}".format(mat_scores_rp3.min()))
        print("max = {}".format(mat_scores_rp3.max()))
        print("average = {}".format(mat_scores_rp3.mean()))'''

        # normalization
        mat_scores_slim /= mat_scores_slim.max()
        mat_scores_rp3 /= mat_scores_rp3.max()

        self.mat_scores_slim = mat_scores_slim
        self.mat_scores_rp3 = mat_scores_rp3
        '''print("slim scores stats:")
        print("min = {}".format(mat_scores_slim.min()))
        print("max = {}".format(mat_scores_slim.max()))
        print("average = {}".format(mat_scores_slim.mean()))

        print("rp3 scores stats:")
        print("min = {}".format(mat_scores_rp3.min()))
        print("max = {}".format(mat_scores_rp3.max()))
        print("average = {}".format(mat_scores_rp3.mean()))'''

        # np.save(path_slim, arr=mat_scores_slim)
        # np.save(path_rp3, arr=mat_scores_rp3)

        self.score_matrix = alpha * mat_scores_slim + (1 -
                                                       alpha) * mat_scores_rp3

    def _compute_item_score(self, user_id_array, items_to_compute=None):
        return self.score_matrix[user_id_array]