سؤال

أريد أن أحصل على منظور المجتمع في هذا الشأن. إذا كان لدي عملية مرتبطة بشكل كبير DB/IO ، فما مدى ذكاء مسارات العملية الفردية باستخدام المكتبة الموازية للمهمة؟

سأستخدم مثالًا ... إذا كان لدي مجموعة من العناصر ، وأحتاج إلى القيام بالعمليات التالية

  1. الاستعلام عن ديسيبل لقائمة العناصر
  2. قم ببعض عمليات التجميع لتجميع عناصر معينة بناءً على قائمة ديناميكية من المعلمات.
  3. لكل نتيجة مجمعة ، الاستعلام عن قاعدة البيانات لشيء بناء على النتيجة المجمعة.
  4. لكل نتيجة مجمعة ، قم ببعض الحسابات الرقمية (سيحدث 3 و 4 بشكل متتابع).
  5. قم ببعض الإدراج والتحديثات للنتيجة المحسوبة في #3
  6. قم ببعض الإدراج والتحديثات لكل عنصر يتم إرجاعه في #1

من الناحية المنطقية ، يمكنني التوازي مع رسم بياني للمهام في الخطوات رقم 3 ، رقم 5 ، رقم 6 كعنصر واحد ليس له تأثير على النتيجة السابقة. ومع ذلك ، سينتظر كل من هذه الأشياء على قاعدة البيانات (SQL Server) وهو أمر جيد وأنا أفهم أنه لا يمكننا معالجة إلا بقدر ما سيسمح لنا SQL Server بذلك.

لكنني أريد توزيع المهمة بشكل منطقي على الجهاز المحلي بحيث يتم معالجتها بأسرع ما تتيح لنا قاعدة البيانات دون الحاجة إلى انتظار أي شيء في نهايتنا. لقد قمت ببعض النموذج الأولي الهام حيث أقوم باستبدال مكالمات DB باستخدام thread.sleeps (لقد جربت أيضًا بعض الاختلافات مع .spinwait ، والتي كانت أسرع بمليون مرة) ، والنسخة الموازية هي أسرع من التنفيذ الحالي الذي هو متسلسل بالكامل وليس موازية على الإطلاق.

ما أخشى أن يضع الكثير من الضغط على خادم SQL ... هل هناك أي اعتبارات يجب أن أفكر فيها قبل أن أذهب بعيدًا جدًا عن هذا المسار؟

هل كانت مفيدة؟

المحلول

هناك خيار آخر هو إنشاء خط أنابيب بحيث تحدث الخطوة 3 للمجموعة الثانية في نفس الوقت مثل الخطوة 4 للمجموعة الأولى. وإذا كنت تستطيع التداخل في التحديثات في الخطوة 5 ، فقم بذلك أيضًا. وبهذه الطريقة ، تقوم بالوصول إلى SQL المتزامن ومعالجته ، ولكن ليس الإفراط في تحديد قاعدة البيانات لأن لديك فقط عمليتين متزامنين يحدثان في وقت واحد.

لذلك يمكنك القيام بخطوات 1 و 2 بالتسلسل (أفترض) للحصول على مجموعة من المجموعات التي تتطلب المزيد من المعالجة. ثم. يبدأ موضوعك الرئيسي:

for each group
  query the database
  place the results of the query into the calc queue

خدمات الخيط الثاني قائمة انتظار النتائج:

while not end of data
  Dequeue result from calc queue
  Do numeric calculations
  place the results of the query into the update queue

يخدم الخيط الثالث قائمة انتظار التحديث:

while not end of data
  Dequeue result from update queue
  Update database

ال System.Collections.Concurrent.BlockingCollection<T> هو قائمة انتظار فعالة للغاية لهذا النوع من الأشياء.

الشيء الجميل هنا هو أنه إذا كان بإمكانك توسيع نطاقه إذا كنت تريد إضافة مؤشرات ترابط حساب متعددة أو موضوعات استعلام/تحديث إذا كان خادم SQL يمكنه التعامل مع معاملات أكثر تزامن.

أستخدم شيئًا مشابهًا جدًا لهذا في برنامج الدمج/التحديث اليومي ، مع نتائج جيدة جدًا. لا تستخدم هذه العملية بالذات SQL Server ، بل ملف I/O القياسي ، لكن المفاهيم تترجم جيدًا.

نصائح أخرى

إذا كان الإصدار الموازي أسرع بكثير من الإصدار التسلسلي ، فلن أشعر بالقلق بشأن الضغط على خادم SQL الخاص بك ... ما لم تكن المهام التي تقوم بها بالطبع أولوية منخفضة مقارنة ببعض العمليات المهمة الأخرى أو الزمنية التي هي أيضًا يتم تنفيذها على خادم DB.

إن وصفك للمهام غير مفهومة جيدًا من قبلي ، لكن يبدو أن المزيد من هذه المهام كان ينبغي أن يتم تنفيذها مباشرة في قاعدة البيانات (أفترض أن هناك تفاصيل تجعل ذلك غير ممكن؟)

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top