第一章:GraphRAG 的系統架構 1. 索引建立(Indexing Time) GraphRAG 的第一階段是將原始文本資料建構成圖索引(Graph Index),透過分塊、實體關係抽取、社群檢測等流程,為後續查詢做準備。 A. 文本分塊(Text Chunking) 目的 將大規模文本資料切分成較小片段(chunks),以適配 LLM 的上下文長度限制 同時避免過度切割造成關鍵資訊斷裂 分塊策略 固定長度切割: 每個 chunk 約 600~1000 tokens 適用於一般性文本 語義切割: 利用段落、標題或斷句等結構分割 適合段落結構明確的領域文本(如論文、技術報告) 混合式策略: 先依語義切割,再輔以固定長度控制,確保文本量相對均衡 建議:針對技術文件、新聞報導等,嘗試 600~800 tokens 的固定長度切割並保留 50~100 tokens 重疊,通常能兼顧上下文完整性與LLM 容量。 代碼示例 def split_into_chunks(text, chunk_size=600, overlap=100): chunks = [] start = 0 while start < len(text): end = min(start + chunk_size, len(text)) chunk = text[start:end] chunks.append(chunk) start += (chunk_size - overlap) # 保留部分重疊 return chunks 小結 透過合理的分塊策略,可確保後續的實體/關係抽取不會因關鍵資訊被截斷而遺漏,同時能有效使用 LLM 的上下文容量。 B. 實體/關係抽取(Entity & Relation Extraction) 目的 使用 LLM 從文本塊中提取「實體」(如人名、機構、產品)與「關係」(如合作、投資、競爭) 建立知識圖譜所需的節點與邊 Prompt 設計建議 明確列出目標:請 LLM 尋找重要的實體和它們之間的關聯 格式化輸出:可使用 JSON、三元組、TSV 等,後續便於程式處理 多輪檢查(Gleanings):再次詢問 LLM 是否遺漏了某些實體或關係 實體合併(Entity Merging) 挑戰:相同實體可能以不同名稱出現(如「Google LLC」與「Google」) 對策: 擬定規則或利用 LLM embeddings 判斷相似度,將重複實體進行合併 可在抽取後進行一次全局掃描,將相似度高的節點標記為相同實體 常見錯誤與處理方法 LLM 幻覺:模型可能捏造關係;可透過要求來源佐證或多輪驗證減少此情況 抽取過於籠統:Prompt 不明確導致 LLM 只回傳非常籠統的實體,需在提示中指定要辨識的對象屬性、範圍 小結 實體/關係抽取是建構圖索引的關鍵步驟,成功與否取決於 Prompt 設計、重複實體合併,以及對模型幻覺的防範措施。 C. 建構圖索引與屬性處理 節點(Nodes) 即抽取出的實體,每個節點可包含多種屬性(如描述、時間) 邊(Edges) 即實體之間的關係,可設定加權(如關聯度、共現次數) 屬性(Attributes) 包括事件、狀態、地理資訊等,用於豐富圖的可查詢度 性能優化 若實體/關係數量極大,可考慮用資料庫(如 Neo4j、NebulaGraph)來儲存 排序或過濾「低頻節點」以減少雜訊 小結 建構圖索引是將抽取結果結構化的過程,良好的資料結構與資料庫選擇能提高後續查詢效率並減少維護成本。 D. 社群檢測(Community Detection) Leiden 演算法 目的:將圖拆分成若干「社群(Communities)」,使得社群內節點連結緊密、社群間連結較弱 多層級(C0~C3): C0:根社群或較粗粒度主題 C1、C2:依序深入細分領域 C3:最細節的主題分群 參數調整指南 Resolution:決定社群的大小與數量 Randomization:多次迭代以取得穩定且高模組化度(Modularity)的劃分 社群品質評估 Modularity:越高代表社群更具凝聚力 Node Coverage:確保大多數節點分配到合理的社群中 人工作驗:針對重要主題進行人工抽樣驗證 社群摘要 將每個社群內容再次用 LLM 壓縮成簡短描述,後續查詢可直接引用 若層級深,摘要層層相依,可避免 Token 過度消耗 可視化示例 +-----------+ +-----------+ | 社群A | <----->| 社群B | +-----------+ +-----------+ | \ / | | \ / | | \ ... / | | +-----------+ | | 社群C | +-------------------------+ 圖中顯示各社群之間的邊連結程度,C0~C3 則視不同粒度切換。 小結 社群檢測是 GraphRAG 與傳統 RAG 最大的差異之一,能夠將龐大的知識圖分門別類,進而支援更精準的「全局」或「局部」查詢。 2. 查詢處理(Query Time) 在完成索引建立後,查詢處理階段則透過社群摘要與 Map-Reduce 生成最終答案。 A. 查詢解析與社群選擇 查詢解析 分析查詢的主題、範圍、細節需求 若查詢較宏觀,可直接從 C0 或 C1 社群著手 若查詢需要細節,考慮 C2、C3 社群選擇標準 語義相似度:用嵌入檢索找最符合查詢意圖的社群 社群大小:確保答案不會因社群過大而過度冗長,也不會過度切割失去上下文 小結 合適的社群選擇能大幅降低 Token 消耗,也提高答案的聚焦度;對更複雜的查詢,可以多個社群同時參與。 B. Map-Reduce Summarization Map 步驟 針對每個相關社群摘要,分別詢問 LLM:「此社群對該查詢有何回答?」 要求 LLM 輸出回答及打分(score, 0-100),分數過低者直接排除 Reduce 步驟 將分數高的部分答案,依序加入新上下文 在 Token 容許範圍內,融合所有局部答案,讓 LLM 最終總結成全局回答 代碼示例(簡化) def map_reduce_query(query, community_summaries, llm): partial_answers = [] # Map for summary in community_summaries: ans, score = llm.answer_with_score(query, summary) if score > 0: partial_answers.append((ans, score)) # Sort by score desc partial_answers.sort(key=lambda x: x[1], reverse=True) # Reduce final_context = "" for ans, sc in partial_answers: if len(final_context) + len(ans) < TOKEN_LIMIT: final_context += ans + "\n" else: break global_answer = llm.generate_final(query, final_context) return global_answer 小結 透過 Map-Reduce,不同社群內容能被同時考量,在降低 Token 消耗的同時,最大程度保留全局細節。 3. 實踐練習/思考問題 文本分塊實踐 選擇一份 2,000 字的新聞文件,嘗試以 固定長度 和 語義切割 兩種方式分塊,比較抽取到的實體/關係是否有差異 Prompt 設計探索 針對同一份 chunk,嘗試不同的 Prompt(如要求輸出 JSON、要求來源佐證、限制回答語氣等),觀察實體抽取精度、幻覺比例 Leiden 參數調整 使用 Python 庫(如 networkx、igraph)對同一份知識圖進行社群偵測,觀察 Resolution 參數改變如何影響社群大小與數量 Map-Reduce 模擬 模擬多社群並行回答並彙整,觀察最終答案的全面性與 Token 開銷 思考:在什麼情況下,會需要更精細的社群劃分(C3),而非使用較高層的 C1 或 C2? 4. 常見問題(FAQ) Q:如果在抽取時,LLM 一直產生「不存在的實體」怎麼辦?A:可在 Prompt 中強調「只限於文本明確提及的內容」,並加入多輪驗證或來源引用。 Q:社群檢測後,某些社群節點數極少或過大怎麼辦?A:可調整 Leiden 演算法的 Resolution,或進行手動合併/拆分。 Q:Map-Reduce 時,若某個社群回答重複度極高,會導致 Token 浪費嗎?A:可以利用同義檢測或打分機制過濾重複答案,同時縮短長度後再整合。 Q:每次查詢都要跑 Map-Reduce,計算量會很大嗎?A:可以先使用語義檢索篩選最相關的社群,再對這些社群進行 Map-Reduce,即可避免遍歷所有。 小結 在本章,我們從 文本分塊、實體/關係抽取、圖索引建構 到 社群檢測 與 查詢處理(Map-Reduce Summarization)做了完整且深入的說明。善用這些技術細節、策略與優化方法,能顯著提升 GraphRAG 在大規模文本分析上的效率與回答品質。 第二章:GraphRAG 與其他方法的比較 1. Naïve RAG 優點:直接性強、實作簡單; 缺點:對「全局、跨文件」問題較差,全面性欠缺。 2. 全文摘要(TS, Text Summarization) 優點:可整體概括所有內容; 缺點:每次都要處理整個文本,Token 耗費大;易導致重複或過度摘要。 3. GraphRAG 優勢: 結合圖結構+社群檢測,可以在大規模文本上做系統化切分; 透過多層級摘要確保兼顧細節與效率。 挑戰: 圖構建的品質依賴 LLM 抽取效果; 需解決重複實體、幻覺等技術問題。 第三章:實驗與評估 評估指標 Comprehensiveness:答案的覆蓋度 Diversity:是否包含多重面向 Empowerment:是否能幫助使用者更好地理解並判斷 Directness:答案是否直接且切題 常見數據集範例 Podcast transcripts(約百萬 tokens) News articles(約百萬~數百萬 tokens,涵蓋多領域) 比較結果概述 GraphRAG 在「全面性、多樣性」上明顯優於 Naïve RAG; 與全文摘要相比,在效率與可擴充性上也有更佳表現。 第四章:GraphRAG 演算法詳細說明 1. 為何需要子圖(Subgraph)? 在 GraphRAG 的實作中,我們已建立「整體知識圖(Graph Index)」並進行了社群檢測。但當用戶提出複雜或具體問題時(例如「X 企業與 Y 企業的競合關係?」),將整個知識圖直接丟給 LLM 既不現實,也容易引起 Token 限制與無關資訊干擾。因此,需要對知識圖做子圖提取(Subgraph Extraction),只取與查詢最相關的那一小部分,能更有效率且生成更精準的答案。 2. 如何提取 Subgraph? 子圖提取的核心在於「從大圖中篩選出與查詢相關的節點、屬性與邊」,確保查詢上下文足夠而不冗餘。 A. 主要步驟 文本拆分與知識圖構建 透過前幾章所述的步驟(分塊、實體/關係抽取、社群檢測)得到整體知識圖 每個節點皆能連結相應屬性(如描述、時間、引用片段)與邊(如投資、合作、競爭) 查詢與圖的匹配 可利用關鍵詞或語義嵌入(Embedding)先篩選出最相關的節點 以該節點為「起點」,擴張一兩層邊,萃取和查詢強相關的領域 社群檢測結合 若已經有階層化社群(C0, C1, C2, C3),可直接鎖定對應社群並將整個社群當作子圖 或先用語義匹配找到「候選社群」,再擴散到其相鄰社群 過濾與精修 對子圖中出現的低頻節點、多餘關係進行過濾 合併重複實體,並確認邊的方向與描述是否完整 B. 混合式子圖提取:社群 + 語義檢索 社群檢測 先以 Leiden 演算法取得一批主題社群 使用「查詢 → 社群摘要」比對語義相似度,選出前幾名最吻合社群 子圖擴張 針對該社群內最相關的節點擴張 1~2 層,取得完整關係 形成子圖 將此社群內節點、關係與屬性整合成一個局部知識圖供 LLM 查詢 3. 挑選出合適的子圖 即使能提取子圖,仍需要判斷「哪一部分」最能回答特定問題。這牽涉到社群分層、語義匹配與圖結構的綜合考量。 A. 社群檢測角度 高層級社群(C0, C1) 適合:宏觀、大範圍問題(如「整個新聞語料中最常討論的主題是什麼?」) 好處:節點少、摘要短 限制:細節不足 中層或低層社群(C2, C3) 適合:需要深入了解特定子領域或事件(如「GPT-4 與 Gemini 在訓練方法上有哪些差異?」) 好處:可保留更多細節 限制:Token 使用量大 B. 語義匹配角度 直接匹配查詢關鍵詞 計算節點名稱、描述、屬性與查詢的相似度 快速過濾絕大部分不相關節點 擴展搜索 若查詢為「X 與 Y 在 AI 領域的合作」,可優先匹配「AI」、「X」、「Y」,並找出它們之間的邊 若圖結構顯示 X 與 Y 間同時連到 Z,則擴展到 Z 形成更完整上下文 C. 綜合策略 先用 語義檢索 找到與查詢最相似的社群 依需求深度決定用 C1(較抽象)還是 C2/C3(更細緻) 針對該社群或該節點做 1~2 層邊的擴張,最終形成合適的子圖 關鍵思維:避免「子圖過小導致資訊不足」與「子圖過大導致 Token 浪費與噪音」。 4. 取出子圖後,如何轉變成 LLM 提示字? 獲得子圖(包含節點、屬性與邊)後,仍需轉換成 LLM 可理解並給出適當回答的Prompt。這關鍵步驟包括: A. 選擇合適的表示格式 自然語言描述 用一般文字敘述子圖內容,如「OpenAI 與 Microsoft 之間的合作關係…」 優點:易於大多數 LLM 理解 缺點:若子圖龐大,可能造成 Token 過度消耗 JSON(結構化格式) { "Entities": [ {"Name": "OpenAI", "Type": "Company"}, {"Name": "GPT-4", "Type": "AI Model"} ], "Relations": [ {"Source": "OpenAI", "Relation": "開發", "Target": "GPT-4"} ] } 優點:LLM 工具介面或 Function Calling 容易解析 缺點:需要 LLM 具備良好的 JSON 處理能力 三元組(Triples) (OpenAI, "開發", GPT-4) (Google, "開發", Gemini) (OpenAI, "競爭", Google) 優點:精簡且適合圖邏輯推理 缺點:有時需要更多敘事描述,LLM 才能產生流暢文本 B. Prompt 設計與上下文控制 上下文控制 明確向 LLM 說明:「以下是一個子圖資訊,請基於此回答問題…」 若子圖資訊量大,可依 Token 限制拆分成多段進行Map-Reduce Summarization 保留關鍵屬性 指明實體的核心屬性(如「發表年份: 2023」) 盡量避免過量細節淹沒關鍵資訊 對齊查詢需求 若查詢為比較兩家公司的合作與競爭,Prompt 中必須清晰標示它們之間的邊關係 5. 必須同時匹配 Entity、Attribute、Edge 的原因 在提取子圖與 Prompt 設計時,往往不只匹配節點(Entity),還需要同時匹配節點屬性(Attribute)與邊(Edge): 確保查詢上下文的完整性 僅有節點名稱往往不夠,需要屬性(如時間、角色)與邊(關係敘述)來回答「誰做了什麼?何時?為何?」等 提供 LLM 足夠的語義線索 關係對於推斷因果、比較及歸納性問題尤其重要 6. 綜合範例:子圖提取與 Prompt 轉換 假設查詢為:「2023 年有哪些科技公司發布 AI 模型?它們在新聞裡被如何比較?」 語義檢索: 找到與「AI 模型」「2023」「科技公司」相關度高的社群(如 C2) 提取子圖: 在該社群中匹配「OpenAI, GPT-4, Microsoft, Google, Gemini」,萃取它們互相的關係 過濾、合併: 可能合併「Microsoft」和「MS」,移除不相關節點 轉成 Prompt(JSON 格式範例): { "Entities": [ {"Name": "OpenAI", "Type": "Company"}, {"Name": "GPT-4", "Type": "AI Model", "Released": 2023}, {"Name": "Google", "Type": "Company"}, {"Name": "Gemini", "Type": "AI Model", "Released": 2023} ], "Relations": [ {"Source": "OpenAI", "Relation": "開發", "Target": "GPT-4"}, {"Source": "Google", "Relation": "開發", "Target": "Gemini"}, {"Source": "OpenAI", "Relation": "競爭", "Target": "Google"} ] } LLM 回答: 針對該 JSON Prompt,LLM 得以生成對比敘述:哪幾家於 2023 年發布模型,模型差異何在,市場反響如何等 7. 常見問題(FAQ) Q:只抽取最相似的節點而忽略邊會怎樣?A:容易失去上下文與關聯線索,LLM 無法理解實體之間關係,導致回答不完整或錯誤。 Q:社群劃分顆粒度如何拿捏?A:可先用高層(C1)回答宏觀問題,若使用者需更深層細節,再下鑽到 C2/C3。 Q:子圖中重複實體太多,怎麼處理?A:可使用相似度方法合併重複實體,或透過命名標準(Normalize)精準比對。 Q:Prompt 是否越長越好?A:不盡然。過度冗長會消耗 Token、分散注意力;需在「訊息完整度」與「語料大小」之間取得平衡。 8. 小結與建議 子圖提取是 GraphRAG 中將「大型知識圖」轉化為「與查詢緊密相關子集」的關鍵。 挑選合適子圖需要考慮社群層次、語義檢索結果,以及查詢本身所需的細節深度。 轉換成 LLM 提示字時,可選「自然語言」「JSON」「三元組」等格式,並控制上下文長度與重點屬性。 同時匹配 Entity、Attribute、Edge才能讓 LLM 充分理解子圖的意涵,回答複雜問題時尤其必要。 第五章:未來發展與研究方向 與對話式系統結合 支援多輪對話,動態選取或下鑽(Drill-down)至更細社群。 Causal/Temporal Reasoning 在知識圖上增加因果關係或時間序列分析,回答「為什麼」「何時」類問題。 跨模態擴充 支援影像、音訊等多模態資料,建立圖索引時同時整合文字與視覺資訊。 事實驗證(Fact-checking) 引入引用與佐證機制,防止 LLM 幻覺影響回答正確性。 第六章:總結 GraphRAG 的核心價值:透過「知識圖索引 + 社群檢測 + Map-Reduce Summarization」機制,有效解決 RAG 在「全局性查詢」上的不足。 主要貢獻: 階層式社群摘要:可依查詢需求選擇適當粒度; Map-Reduce:兼顧回答的廣度與深度; 可拓展:可與現有語義搜索或圖演算法整合。 未來趨勢: 結合大模型與知識圖譜的應用正迅速發展,GraphRAG 是一條新興路徑,有潛力應用於智慧企業、媒體分析、科學研究等多方領域。 參考文獻與延伸讀物 From Local to Global: A Graph RAG Approach to Query-Focused Summarization (Preprint, 2024) Lewis et al. (2020). Retrieval-Augmented Generation for Knowledge-Intensive NLP Tasks Traag et al. (2019). From Louvain to Leiden: guaranteeing well-connected communities Fortunato (2010). Community detection in graphs: A survey Ram et al. (2023). In-Context Retrieval-Augmented Language Models