Динамическая фильтрация векторов по идентификатору сообщества в Faiss для улучшения поиска по сходству
У меня есть вариант использования, когда мне нужно динамически исключить определенные векторы на основе определенных критериев, прежде чем выполнять поиск по сходству с помощью Faiss. Я изучил репозиторий Faiss GitHub и столкнулся с проблемой, тесно связанной с моим требованием. В одном из ответов подчеркивалось, что прямая фильтрация векторов может отрицательно повлиять на производительность. Вместо этого они предложили использовать альтернативное решение с использованием IDSelector. Я хотел бы попробовать фильтровать векторы с помощью IDSelector.
Here is a description of my use case:
Давайте рассмотрим таблицу с 1000 записями, где каждая запись соответствует строке в таблице SQL. Каждая запись имеет такие поля, как messageId, message и CommunityId. Эти поля позволяют нам группировать сообщения на основе идентификатора сообщества. Теперь я проиндексировал все 1000 записей. Во время поиска по сходству, когда запрос поступает от определенного сообщества, я хочу искать только внутри соответствующего сообщества, а не во всех сообществах.
As mentioned, there is a workaround suggested:
«Фильтрация должна основываться на идентификаторах векторов». Однако я не уверен в процессе включения идентификатора сообщества в идентификатор вектора и в том, как эффективно фильтровать записи на основе идентификатора сообщества.
os.environ['OPENAI_API_KEY'] = 'key'
messages = ["Hello, world!", "How are you?", "Greetings!","How are you"]
community_ids = [1, 2, 3, 1]
class CommunityIDSelector(faiss.IDSelector):
def __init__(self):
pass
def is_member(self, id):
return community_ids[id] == 1
id_selector = CommunityIDSelector()
embs = []
embeddings = OpenAIEmbeddings()
for message in messages:
embs.append(embeddings.embed_query(text=message))
vectors = np.array(embs)
metadata = np.array(community_ids)
concatenated_vectors = np.concatenate((vectors,metadata[:,np.newaxis]),axis=1)
index = faiss.IndexFlatL2(concatenated_vectors.shape[1])
index.add(concatenated_vectors)
target_community_id = 1
query_vector = np.array([embeddings.embed_query(text='I am good')])
# Prepare query vector with target communityId
query_metadata = np.array([[target_community_id]])
concatenated_query = np.concatenate((query_vector, query_metadata), axis=1)
k = 3
distances, indices = index.search(concatenated_query, k,id_selector)
print("Filtered Messages:")
Questions:
- Как включить идентификатор сообщества в идентификатор вектора?
- Как я могу фильтровать записи по идентификатору сообщества?