TwKit
正在载入
TwKit

# 問自家文件還一本正經胡說八道?你少了讓模型先翻書這一步 模型回答自家文件裡的問題卻張口就來,不是模型笨,是你沒給它翻書的機會。RAG 的做法很直白:回答… · @swordBluesy · TwKit

@swordBluesy

# 問自家文件還一本正經胡說八道?你少了讓模型先翻書這一步 模型回答自家文件裡的問題卻張口就來,不是模型笨,是你沒給它翻書的機會。RAG 的做法很直白:回答之前,先從你的文件裡撈出相關段落,再把段落和問題一起交給模型。這篇不用任何框架,120 行 Python 就把整套東西做出來。原文 2026 年 10 月 28 日發布。 ## 這篇解決什麼 成品是一個命令列程式 http://rag.py,兩個命令:python http://rag.py index docs/ 負責把文件做成索引,python http://rag.py ask "What is our refund policy?" 負責回答。每個回答都帶引用,像 [docs/refunds.md#0] 這樣,任何一句話都能回頭查到出處。整個程式分兩個階段:索引只在文件變化時跑一次,查詢是每次提問都跑。 ## 動手步驟 第一步,建專案、裝依賴。Python 3.10 以上(程式碼用了 list[str] 這種寫法),建虛擬環境,pip install openai numpy,OpenAI 金鑰放環境變數 OPENAI_API_KEY,絕對不要寫進程式碼。嵌入模型用 text-embedding-3-small,預設回 1536 維向量;對話模型原文用 gpt-6-luna,也說了換任何當前對話模型都行,用環境變數 CHAT_MODEL 就能換。 第二步,放幾份範例文件。建 docs 資料夾,放 refunds.md(30 天內全額退款、之後只退商店積分)和 shipping.md(標準 3 到 5 個工作日、快遞 1 到 2 個工作日另收費)當測試資料。 第三步,載入文件。load_documents() 遞迴走訪資料夾,只留 .txt 和 .md,把檔案路徑當成來源一起存下來,路徑以後就是每條回答的引用。 第四步,切塊。chunk_text() 把文字按段落打包成約 1000 字元一塊,每塊帶 200 字元的重疊,邊界上的句子就不會被切斷。整份文件塞進一個向量會把語義磨糊,全部塞進提示詞又浪費 token,切塊就是在這兩者之間取平衡。1000 和 200 只是起點,要拿真實問題去調。 第五步,做嵌入、存索引。embed() 用 OpenAI 嵌入介面,一次送一批(每批 100 塊),介面限制是單條輸入 8192 token、單次請求合計 300000 token,100 塊約 1000 字元的量遠在限制內。向量先做歸一化,這樣餘弦相似度就變成一次點積。build_index() 把向量存成 vectors.npy、把塊文字和元資料按同樣順序存成 chunks.json,第 i 行向量就是第 i 條記錄的嵌入,行號對不上,整個索引就廢了。 第六步,查詢時先撈再答。retrieve() 先把問題也嵌成向量,一次矩陣乘法算出它和所有塊的相似度,取前 4 塊,但分數低於 0.2 的不要,避免把不相關的文字塞給模型。answer() 把撈到的塊連同編號貼進提示詞,指令寫死:只能用這些上下文回答。原文提醒兩件事:問題必須用同一個嵌入模型嵌,不同模型的向量不在同一個空間,沒法比;分數門檻別迷信 0.2,拿幾個真問題印出分數再自己定。 ## S1哥觀點 這篇最漂亮的地方是它把「向量資料庫」去神祕化了:兩個檔案,一個存向量、一個存文字,就是一個能用的索引。很多人一聽 RAG 就先去搭一整套框架和服務,結果文件還沒幾份,架子已經比房子大。 爭論點在這裡:有人說不用框架就是玩具,上生產遲早要重寫。真相是,玩具和原型的差別不在框架,在你有沒有跑通過一次完整的撈取和引用。先讓 120 行跑起來、回答帶引用,再談要不要上框架,順序不能反。 原文連結:https://www.thetechlane.in/ai/build-a-simple-rag-application-using-python 原文:TheTechLane(由 S1哥 編譯)

曝光 243 · 评论 2 · 点赞 2 · 书签 0

查看原帖