아 글은 On Hybrid Search 를 보고 정리한 글입니다.


Hybrid Search 의 정의:

  • 일반적으로 둘 이상의 검색 알고리즘을 사용하는 경우를 하이브리드 검색이라고 할 수 있음.
  • 대표적으로 알려져 있는 Hybrid Search 는 벡터 검색과 키워드 기반 검색의 조합을 말함. (이 글에서 다루는 내용)
  • 이것 이외에도 밀집 벡터(dense vectors)와 희소 벡터(sparse vectors)의 혼합도 하이브리드 검색이라고도 할 수 있음. (이건 이후에 소개)

 

 

벡터 검색의 장점:

  • 다국어 및 멀티모달 검색에 유용
  • 오타가 있거나 모호한 짧은 텍스트 처리에 효과적임.
  • 의미 기반의 유사도 검색 가능
  • 특화된 도메인에서 튜닝된 인코더 모델 사용해서 효과적인 유사도 검색을 할 수도 있음.

 

 

Keyword Search 의 필요성:

  • 단어의 의미와 관계없이 단어 자체로 검색하는 경우
  • 제품명, 인명, 부품 번호 등을 검색에 사용하는 경우
  • 타이핑 검색 중 처음 몇 글자만 입력된 상태에서 벡터 검색을 사용하기 어려울 때
  • 문서에서 특정 용어의 정확한 출현을 찾을 때

 

 

Hybrid Search 의 필요성:

  • Vector Search 의 장점과 Keyword Search 의 장점을 모두 취하기 위해서.

 

 

Typing 검색에서 벡터 검색과 통합하는 방법:

  • 키워드 검색에서 마땅한 결과를 찾지 못했을 때 Vector Search 를 사용하도록. (Fallback 전략)
  • 작동 원리: (여기서는 타이핑 검색을 하는 경우를 다룸.)
      1. 먼저 MeiliSearch로 빠른 키워드 검색을 수행함.
      1. 결과가 충분하거나 적절하면 키워드 검색 결과를 반환한다.
      1. 그렇지 않으면 쿼리를 벡터로 인코딩하고 Qdrant를 사용하여 벡터 검색을 수행한다.
async def search(query: str):
    # Get fast results from MeiliSearch
    keyword_search_result = search_meili(query)

    # Check if there are enough results
    # or if the results are good enough for given query
    if are_results_enough(keyword_search_result, query):
        return keyword_search

    # Encoding takes time, but we get more results
    vector_query = encode(query)

    vector_result = search_qdrant(vector_query)
    return vector_result

 

 

웹 검색과 같은 문서 검색에서도 Vector Serach 와 통합할 수 있는 방법은 많지만 Best Practices 는 아직까지 없음. 계속해서 연구중이고, 이후에 여러 실험을 해보고 알려준다고 함.

 

 

BM25 와 qdrant vector search 를 다음과 같이 선형 조합 공식으로 구성하는 건 그렇게 효과적이지 않음:

  • final_score = 0.7 * vector_score + 0.3 * full_text_score
  • 왜냐하면 BM25 점수와, qdarant scoring 의 조합으로 검색을 한다라고 했을 때 검색 쿼리와 관련성이 있는 문서와 관련성이 없는 문서를 명확하게 선으로 나눌 수 없음.
  • 즉 어떻게든 선형 방정식을 만들어도 관련성이 있는 문서와 관련성이 없는 문서는 50%로 정도로 분리시킬거임. 그러니까 무작위 분류와 큰 차이 안난다는거지.

 

 

Re-ranking 알고리즘을 적용하는 방법:

  • Vector Search, Keyword Search 를 병렬로 실행한 후 결과를 종합해서 Cross Encoder 모델로 재랭킹을 매기는 매커니즘을 통해서 검색 품질을 향상 시키는 것.
  • Cross Encoder 모델:
    • 딥러닝 모델을 이용함.
    • 일반적인 키워드 검색과 벡터 검색보다는 느림.
    • 문서와 쿼리의 입력 쌍을 받고나서, 쿼리가 문서와 모든 상호작용에 대해서 연관성을 측정함. 기존의 키워드 검색은 중요한 단어의 출현 빈도만 측정하고, 벡터 검색은 벡터 비교만을 했다면 이런 Cross Encoder 모델은 더 복잡한 과정을 거친다. 단순히 bank 라는 키워드만 하더라도 cross encoder 모델은 문맥과 비교해서 이게 은행으로 쓰였는지, 강둑으로 쓰였는지 비교할 것.
    • 이 모델은 사용자의 선호도를 측정할 수 있는 데이터로 학습이 될거임. 주로 사용할 수 있는 데이터가 사용자의 클릭 스트림 데이터 (사용자가 웹사이트나 앱에서 수행하는 모든 클릭과 상호작용) 이 될거고.
async def search(query: str):
    keyword_search = search_keyword(query)
    vector_search = search_qdrant(query) 
    all_results = await asyncio.gather(keyword_search, vector_search)  # parallel calls
    rescored = cross_encoder_rescore(query, all_results)

 

 

다음 3가지 테스트 군을 실험해서 어느게 가장 좋은 성능이 나오는지 보자:

  • Vector search with Qdrant:
    • All the documents and queries are vectorized with all-MiniLM-L6-v2 model, and compared with cosine similarity.
  • Keyword-based search with BM25:
    • All the documents are indexed by BM25 and queried with its default configuration.
  • Vector and keyword-based candidates generation and cross-encoder reranking
    • Both Qdrant and BM25 provides N candidates each and ms-marco-MiniLM-L-6-v2 cross encoder performs reranking on those candidates only. This is an approach that makes it possible to use the power of semantic and keyword based search together.

 

 

실험에 사용될 Quality metrics:

  • NDCG@5, NDCG@10:
    • 이상적인 순위와 비교해서 현재 순위가 얼마나 좋은가? 를 나타내는 지표임.
    • 1에 가까울수록 현재 순위가 이상적인 순위에 가깝다는 것을 의미한다.
  • DCG@5, DCG@10:
    • 관련성 높은 문서가 상위에 얼마나 잘 배치되어 있는가? 를 나타내는 지표임.
    • 높을수록 관련성 높은 문서가 상위에 잘 배치되어 있다는 것을 의미함.
  • MRR@5, MRR@10:
    • 첫 번째로 관련있는 문서가 얼마나 높은 순위에 있는가? 를 나타내는 지표임
    • 높을수록 사용자가 원하는 정보를 빨리 찾을 수 있다는 것을 의미한다.
  • Precision@5, Precision@10:
    • 검색 결과가 얼마나 정확한가? 를 나타내는 지표임.
    • 높을수록 불필요한 결과가 적다라는 뜻임.
  • Recall@5, Recall@10:
    • 관련 있는 문서를 얼마나 많이 찾아왔는가? 를 나타내는 지표임.
    • 높을수록 누락된 문서가 없다라는 거임.

 

 

Benchmark 에 사용될 데이터 셋은 다음과 같음:

 

 

Benchmark 결과:

 

 

 

Wrap up:

  • 각 검색 시나리오마다 최상의 결과를 얻기 위해 특화된 도구가 있다라는 걸 알아야 함. 이걸 바탕으로 여러 검색 방식을 결합/조정 하는게 중요하다.
  • 기존 검색 스택에 벡터 검색을 도입하는 것은 점진적인 단계로 가능함.
  • 전문 검색(Fulltext Search) 로는 한계가 있음. 분명 이것만으로는 모든 관련 문서를 찾지 못하고, 예상하지 못한 쿼리를 지원하지 못한다.
  • 사용자가 데이터베이스에 있는 것과 다른 용어를 사용하는 경우가 있는데 이런 건 딥러닝 임베딩 모델을 이용해서 해결할 수 있음.
  • 전문 검색과 벡터 검색을 결합하고 추가적인 재순위화 단계 (re-ranking) 를 도입하는 방식의 하이브리드는 성능이 좋음.

+ Recent posts