مع انتقال الذكاء الاصطناعي من النماذج التجريبية إلى التطبيقات الإنتاجية، تزداد الحاجة بشكل غير مسبوق إلى استرجاع البيانات منخفض زمن الاستجابة وعالي الإنتاجية. غالباً ما تواجه محركات البحث التقليدية وقواعد البيانات العلاقية صعوبات في التعامل مع أبعاد تضمينات التعلم الآلي الحديثة. هنا يبرز بحث المتجهات في Redis (Redis Vector Search)، حيث يقدم مزيجاً فريداً من سرعة الذاكرة العشوائية وقدرات المتجهات القوية.
لماذا Redis لبحث المتجهات؟
في جوهره، يُعد Redis مخزن البيانات في الذاكرة العشوائية الرائد عالمياً. من خلال الاحتفاظ بالبيانات في ذاكرة الوصول العشوائي (RAM) بدلاً من القرص الصلب، يلغي Redis اختناقات الإدخال/الإخراج (I/O) التي تعاني منها قواعد البيانات المعتمدة على الأقراص. وعند إضافة قدرات بحث المتجهات إلى هذا الأساس، تحصل على أوقات استجابة أقل من المللي ثانية لعمليات البحث عن التشابه. وهذا أمر حاسم للتطبيقات مثل التخصيص في الوقت الفعلي، والبحث الدلالي، وأنظمة التوليد المعزز بالاسترجاع (RAG)، حيث يرتبط تجربة المستخدم ارتباطاً مباشراً بزمن استجابة الاستعلام.
على عكس قواعد بيانات المتجهات المتخصصة التي قد تتطلب بنية تحتية منفصلة وطبقات مزامنة، يتيح لك بحث المتجهات في Redis تخزين المتجهات جنباً إلى جنب مع بيانات المفاتيح-القيم التقليدية، أو السلاسل النصية، أو القواميس (Hashes). وهذا يبسط البنية المعمارية من خلال تقليل الحاجة إلى أنماط تجزئة البيانات والاستمرارية متعددة اللغات (polyglot persistence).
التنفيذ باستخدام Python
يبدأ استخدام بحث المتجهات في Redis بسهولة، خاصة مع مكتبة redis-py الحديثة. توفر المكتبة طرقاً بديهية لإنشاء الفهارس، وإدراج المتجهات، وإجراء الاستعلامات باستخدام Redis Stack.
أولاً، تأكد من تشغيل مثيل لـ Redis Stack. ثم، يمكنك تعريف فضاء متجهي باستخدام خوارزمية HNSW (العالم الصغير القابل للتنقل الهرمي)، والتي توفر توازناً ممتازاً بين الدقة والسرعة.
import redis
import json
# الاتصال بـ Redis
client = redis.Redis(host='localhost', port=6379, decode_responses=True)
# تعريف معلمات المتجهات
DIM = 1536 # مثال لتضمينات OpenAI
DISTANCE_METRIC = "COSINE"
# إنشاء فهرس المتجهات
client.ft("idx:vector").create_index(
fields=(
redis.commands.vector.Field("vector", "VECTOR", "HNSW", {
"TYPE": "FLOAT32",
"DIM": DIM,
"DISTANCE_METRIC": DISTANCE_METRIC,
"INITIAL_CAP": 1000
})
),
definition=redis.commands.index.IndexDefinition(prefix=["doc:"])
)
# إدراج مستند مع تضمين
embedding = [0.1] * DIM # تضمين مؤقت
payload = {"title": "فهم الذكاء الاصطناعي", "content": "الذكاء الاصطناعي يحول..."}
client.hset(
"doc:1",
mapping={
"vector": redis.commands.vector.convert_vector(embedding),
"payload": json.dumps(payload)
}
)
في هذا المثال، نقوم بإنشاء فهرس مسطح (Flat) أو HNSW اعتماداً على الخوارزمية المحددة. يخبر نوع الحقل VECTOR Redis بمعالجة الحقل المحدد كفضاء متجهي عالي الأبعاد. يجب أن يتطابق المعلمة DIM مع طول التضمينات الخاصة بك.
تنفيذ الاستعلامات الدلالية
بمجرد فهرسة البيانات، يكون الاستعلام بسيطاً مثل توفير متجه استعلام. سيقوم Redis بإجراء بحث التشابه وإرجاع الجيران الأقرب مع درجاتهم.
# البحث عن المستندات المشابهة
query_vector = [0.12] * DIM
num_results = 5
results = client.ft("idx:vector").search(
redis.commands.vector.Query(query_vector)
.return_fields("payload")
.dialect(2)
)
for doc in results.docs:
print(f"ID: {doc.id}, Score: {doc.score}, Payload: {doc.payload}")
تشير الدرجة (score) المُرجعة إلى المسافة أو مقياس التشابه (اعتماداً على التكوين)، مما يتيح لك تصفية النتائج الأقل صلة ديناميكياً. هذه القدرة ضرورية لبناء خطوط أنابيب RAG حيث يجب فقط تغذية أجزاء النص الأكثر صلة بالسياق إلى نموذج لغوي كبير (LLM).
الخاتمة
يمثل بحث المتجهات في Redis تطوراً قوياً في بنية البيانات، حيث يدمج سرعة الحوسبة في الذاكرة العشوائية مع تعقيد الاسترجاع المدعوم بالذكاء الاصطناعي. بالنسبة للمطورين الذين يبنيون تطبيقات في الوقت الفعلي، فإنه يوفر مساراً مبسطاً لتنفيذ البحث الدلالي دون العبء التشغيلي لصيانة قواعد بيانات متجهات منفصلة. من خلال الاستفادة من Redis، تضمن أن ميزات الذكاء الاصطناعي الخاصة بك تعمل بنفس سرعة وصول البيانات.