إعادة الترتيب باستخدام نماذج التضمين
كود بايثون لإعادة الترتيب في RAG
إعادة الترتيب هو خطوة ثانية في توليد المحتوى المعزز بالاسترجاع (RAG) الأنظمة, بين الاسترجاع والتكوين.
الصورة أعلاه تُظهر كيف يتخيل Flux-1 dev كُبّات كهربائية في الفضاء الرقمي
.
الاسترجاع مع إعادة الترتيب
إذا قمنا بتخزين الوثائق على شكل إدخالات في قاعدة البيانات المتجهية من البداية - فسيعطي الاسترجاع لنا قائمة بالوثائق المشابهة فورًا.
إعادة الترتيب المستقلة
لكن إذا قمنا أولاً بتنزيل الوثائق من الإنترنت، فقد تتأثر استجابة نظام البحث بتحيزات/خوارزميات مزودي البحث، والمحتوى المدفوع، وتحسين SEO، وغيرها، لذا نحتاج إلى إعادة ترتيب ما بعد البحث.
ما كنت أقوم به -
- الحصول على إدخالات للسؤال البحثي
- الحصول على إدخالات لكل وثيقة. لم يكن من المتوقع أن تتجاوز الوثيقة 8000 رمز من أي حال
- حساب التشابه بين السؤال والإدخالات لكل وثيقة
- ترتيب الوثائق حسب هذا التشابه.
لا توجد قاعدة بيانات متجهية هنا، لنذهب.
كود نموذجي
استخدام Langchain للاتصال بـ Ollama ووظيفة cosine_similarity من langchain. يمكنك فلترة النتائج حسب مقياس التشابه، لكن تذكر أن العتبة ستختلف حسب المجال والنماذج المختلفة للإدخالات ونماذج LLMs.
سأكون سعيدًا إذا كان هذا الكود مفيدًا لك بأي شكل من الأشكال. ترخيص Copy/Paste/UseAnyWayYouWant. تحياتي.
from langchain_core.documents import Document
from langchain_community.embeddings import OllamaEmbeddings
from langchain_community.utils.math import cosine_similarity
import numpy as np
def cosine_distance(a: np.ndarray, b: np.ndarray) -> np.ndarray:
return 1.0 - cosine_similarity(a, b)
def compute_score(vectors: np.ndarray) -> float:
score = cosine_distance(vectors[0].reshape(1, -1), vectors[1].reshape(1, -1)).item()
return score
def list_to_array(lst):
return np.array(lst, dtype=float)
def compute_scorel(lists) -> float:
v1 = list_to_array(lists[0])
v2 = list_to_array(lists[1])
return compute_score([v1, v2])
def filter_docs(emb_model_name, docs, query, num_docs):
content_arr = [doc.page_content for doc in docs]
ollama_emb = OllamaEmbeddings(
model=emb_model_name
)
docs_embs = ollama_emb.embed_documents(content_arr)
query_embs = ollama_emb.embed_query(query)
sims = []
for i, emb in enumerate(docs_embs):
idx = docs[i].id
s = compute_scorel([query_embs, docs_embs[i]])
simstr = str(round(s, 4))
docs[i].metadata["sim"] = simstr
sim = {
"idx": idx,
"i": i,
"sim": s,
}
sims.append(sim)
sims.sort(key=sortFn)
sorted_docs = [docs[x["i"]] for x in sims]
filtered_docs = sorted_docs[:num_docs]
return filtered_docs
أفضل نماذج الإدخال
للمساهمات الخاصة بي، النموذج الأفضل للإدخال حاليًا هو bge-large:335m-en-v1.5-fp16
احتل المكان الثاني النموذجان nomic-embed-text:137m-v1.5-fp16
و jina/jina-embeddings-v2-base-en:latest
.
لكن قم بإجراء اختباراتك الخاصة لمساهماتك وسؤالك.
روابط مفيدة
- نماذج Qwen3 للإدخال وإعادة الترتيب على Ollama: أداء متميز
- https://en.wikipedia.org/wiki/Retrieval-augmented_generation
- قائمة مصطلحات Python
- كيف يتعامل Ollama مع الطلبات المتزامنة
- كتابة محفزات فعالة لنماذج LLMs
- اختبار نماذج LLMs: gemma2، qwen2 و Mistral Nemo
- تثبيت وتكوين Ollama
- مقارنة نماذج LLMs: Mistral Small، Gemma 2، Qwen 2.5، Mistral Nemo، LLama3 و Phi
- قائمة مصطلحات Conda
- قائمة مصطلحات Ollama
- لambdas متعددة الطبقات مع AWS SAM و Python
- اختبار: كيف يستخدم Ollama أداء وحدات المعالجة المركزية من Intel ووحدات المعالجة الفعالة