我正在开发一个模仿 https://www.mtgassist.com/ 的 Python 项目。对于那些不太熟悉的人来说:万智牌是一款集换式卡牌游戏,其中的收藏卡牌可能非常昂贵。该项目应该采用一张卡的名称,并根据几个功能列出具有类似机制(并且希望更便宜)的其他卡,包括描述该卡功能的“oracle_text”。
porter = PorterStemmer()
def tokenizer_stemmer(text: str) -> str:
stop = stopwords.words('english')
return [porter.stem(word) for word in text.split() if word not in stop]
tfidf = TfidfVectorizer(
ngram_range=(1,2)
, tokenizer=tokenizer_stemmer
, stop_words=stopwords.words('english')
)
token_mat = tfidf.fit_transform(df_not_na['oracle_text'])
token_mat
转换为形状为 ~(20_000, 90_000) 的 numpy 数组 (token_arr
),并计算所选卡片与数组中所有卡片之间的欧氏距离(这需要额外的 25 秒) 。最后,我打印出前 5 张“最接近”卡片的名称:token_arr = token_mat.toarray()
distances = []
for _card in tqdm(token_mat):
distances.append(np.linalg.norm(_card - chosen_card_array))
nearest_5 = np.argpartition(distances, 10)[:10]
print(df_not_na.iloc[nearest_5][['name', 'oracle_text']])
我的目标是优化这个过程并减少创建特征向量和计算距离的时间。
我尝试仅使用二元组而不是 ngram_range=(1,2),但效果很小。
我也想过使用 numba,但读到 sklearn/numpy 具有类似的嵌入式功能,并没有多大好处。
还有其他建议也请告诉我! 谢谢
我发现效率低下的两个原因,
改善这一点的方法,