🌟

RAGにおけるチャンキング方法の紹介

2024/03/15に公開

RAGにおいて明確に検索したいドキュメントが存在するにもかかわらず、うまくいかないことが多々あります。

しかしそのような場合に、どの部分が悪いのかがはっきりしないため、修正方法がわからないという方も多いのではないでしょうか。検索性を改善する方法の一つに文書分割にアプローチする方法があります。文章分割はチャンキングという専門用語で呼ばれることが多いです。チャンキングされた後の文書をチャンクと言い、これがRAGにおける検索対象の単位となります。

チャンキングの手法には最適な手法は当然ありませんが、ベーシックな方法は固まりつつあります。ここではそういったベーシックな方法を二つと新しくて興味のそそられる手法を一つ紹介します。

文字数によってチャンキングする方法

これは文字数によるチャンキングは最も一般的に考えることができる方法です。つまり決められた文字数の文章を一つの単位としてインデクシングします。ここで注意する点は、分割されたそれぞれの文章は重なり合わせる方法もあるということです。こうすることにより、インデクシングする量が増えてパフォーマンスに悪影響が出る可能性がある一方で、文間のつながりが良いチャンクも増えるためそこに対しては検索性能が向上します。
こういったパラメーターを決定するには実データで実験をするしかないので、そこは地道に取り組むことをお勧めします。

小区切りによってチャンキングする方法

元文書に何らかの構造がある場合には、それを利用してチャンキングするといい結果が得られるかもしれません。基本的なチャンキングの指針として「適度な文字数、かつ意味的に分割されるようにする」というものがあります。文章の構造を用いてチャンキングすることで、そのような指針を自然と取り入れることができます。
元文章がMarkdown構文で書かれている場合には、この方法を簡単に適用する方法があります。それが小区切りによって分割するという方法です。
LLM系の汎用ライブラリである、Langchainでは下のように実装されています。

markdown_document = "# Foo\n\n    ## Bar\n\nHi this is Jim\n\nHi this is Joe\n\n ### Boo \n\n Hi this is Lance \n\n ## Baz\n\n Hi this is Molly"

headers_to_split_on = [
    ("#", "Header 1"),
    ("##", "Header 2"),
    ("###", "Header 3"),
]
markdown_splitter = MarkdownHeaderTextSplitter(headers_to_split_on=headers_to_split_on)
md_header_splits = markdown_splitter.split_text(markdown_document)

セマンティックチャンキング

これはGreg Kamradtが新しく提案した概念で、RAG関連のフレームワークであるLlamaIndex[https://docs.llamaindex.ai/en/stable/examples/node_parsers/semantic_chunking.html]でも実装されています。
LlamaIndexによると、このチャンキングでは埋め込み類似度を使用して文間の分割位置を決定します。そうすることにより、各分割内で意味的に関連する文が多く含まれることを保証する方法になっています。
最初に紹介した二つの方法と明らかに違う点は、このチャンキング方法だと文の内容を加味できるという点です。言語モデルの文章理解能力を用いてチャンキングするこの方法では、質的に上の二つとは全く違う分割になることが考えられます。

また正規表現や文字数といったハイパーパラメーターの影響も受けづらくなる可能性があります。
ハイパーパラメーターは、定義として異種の文書に対して同一のチャンキング戦略を取る場合に適したチャンクを得るためのパラメーターのことを言います。
なぜハイパーパラメーターの影響を受けないことが、チャンキング方法のメリットになり得るのでしょうか。 
それはパラメーターを変えることなく、多くの文章に対して一定レベルのチャンキングができることになるので、それぞれの最適化を考える時間を削減できるためです。 ハイパーパラメーターが一つの場合には、最適なパラメーターの探索には時間がさほどかかりませんが、二つ三つと増えていくと基本的にその乗数によって探索時間が増加することになるので、非常に面倒になります。

セマンティックチャンカーには通常、汎用の埋め込みモデルを使うことができます。また今後狭ンティックチャンカーのための学習された埋め込みモデルなどが開発されれば、さまざまなチャンキングをモデルが行うこともできると思います。

終わりに

この記事ではRAGにおいて非常に重要なチャンキングについて紹介しました。チャンキングにはさまざまな方法があり、データの特性や活用シーンごとに適した方法が存在します。どの方法が適しているのかは実験してみないとわからない部分が大きいので、まずはシンプルな方法から実践していくことをお勧めします。
またチャンキングをどれだけ良くしたとしても、必要な検索性に届かないことも考えられます。そのような場合には潔く引いて、違う切り口で考えることも必要なのであまり一つの手法にこだわりすぎないことも大切だと思います。
この記事がよかったらいいいねお願いします。

Discussion