مشاركة عبر


مقدمة إلى PLINQ

ما هو استعلام متوازى؟

تم تقديم الاستعلام المتكاملة باللغة (LINQ) في.NET Framework الإصدار 3.0 من ميزات طراز موحد الاستعلام عن أي System.Collections.IEnumerableأو System.Collections.Generic.IEnumerable<T>بيانات المصدر في طريقة نوع اﻷمن. LINQ إلى الكائنات هو اسم LINQ الاستعلامات التي تعمل مع مجموعات في ذاكرة مثل كـ List<T>صفائف. وهذا مقالة المفترض أنه لديك understand أساسية من LINQ. لمزيد من المعلومات، راجع مكون Language-Integrated Query (LINQ).

المتوازية LINQ (PLINQ) هو تنفيذ متوازي نقش LINQ. استعلام PLINQ بطرق كثيرة تشابه غير-متوازى LINQ للاستعلام عن الكائنات. الاستعلامات PLINQ، تماما كمتسلسل LINQالاستعلامات، فتعمل تشغيل أي ذاكرة IEnumerableأو IEnumerable<T>بيانات المصدر، وتم تأجيل التنفيذ، مما يعني أن لا تبدأ تنفيذ حتى الاستعلام هو تعداد. الفرق الأساسي هو أن PLINQ يحاول إجراء استخدم الكامل لكافة المعالجات تشغيل النظام. يقوم بذلك بواسطة تقسيم مصدر بيانات إلى قطاعات، ومن ثم تنفيذ الاستعلام تشغيل كل قطعة من العامل منفصلة مؤشرات الترابط في متوازى تشغيل معالجات متعددة. في كثير من الحالات، متوازى تنفيذ يعني أن تشغيل الاستعلام ملحوظ أسرع.

من خلال متوازى التنفيذ، PLINQ يمكن تحقيق تحسينات الأداء الهامة عبر تعليمات برمجية قديم لأنواع معينة من الاستعلامات، وغالباً ما فقط بواسطة إضافة AsParallelعملية استعلام مصدر بيانات. ومع ذلك، بإمكان parallelism تقديم complexities الخاصة به، و لا تقوم كافة العمليات الاستعلام يعمل بشكل أسرع في PLINQ. في الحقيقة، parallelization فعلا إبطاء بعض الاستعلامات. ولذلك، يجب فهم كيفية تأثير على مشاكل مثل ترتيب متوازى الاستعلامات. لمزيد من المعلومات، راجع فهم زيادةالسرعة في PLINQ.

ملاحظةملاحظة

يستخدم هذه الوثائق تعبيرات لامدا إلى تعريف التفويضات في PLINQ.إذا لم تكن معتاداً على تعبيرات لامدا في C# أو Visual أساسى، راجع لامدا التعبيرات في PLINQ و TPL.

يوفر نظرة عامة حول الفئات PLINQ الرئيسي المتبقي من هذه المقالة، ويتناول كيف إلى إنشاء استعلامات PLINQ. يحتوي كل مقطع على الارتباطات إلى أكثر تفصيلاً أمثلة المعلومات والتعليمات البرمجية.

فئة ParallelEnumerable

System.Linq.ParallelEnumerableيستهدف فئة تقريبا الجميع الوظائف الخاصة PLINQ. و باقي System.Linqيتم تصنيف أنواع مساحة الاسم في تجميع النظام.Core.dll. الافتراضي C# و Visual أساسى مشاريع في ‏‫Visual Studio مرجع تجميع واستيراد مساحة الاسم.

ParallelEnumerableيتضمن تطبيقات الجميع operaإلىrs استعلام قياسي يدعم LINQ إلى الكائنات، على الرغم من أنه بمحاولة لا إلى parallelize كل واحد. إذا لم تكن معتاداً على LINQ، راجع مقدمة حول LINQ.

بالإضافة إلى عوامل تشغيل استعلام قياسي، ParallelEnumerableفئة يحتوي على التعيين من الطرق التي تمكن السلوك الخاصة متوازى التنفيذ. يتم سرد هذه الطرق الخاصة PLINQ في الجدول التالي.

عامل تشغيل ParallelEnumerable

الوصف

AsParallel()

يؤشر إدخال ل PLINQ. تعين أنه يجب أن تكون parallelized بقية الاستعلام، إذا هو المحتملة.

AsSequential()

تحديد أن الجزء المتبقي الاستعلام يجب تشغيل بشكل متسلسل، كاستعلام غير-متوازى LINQ.

AsOrdered()

تعين أن PLINQ يجب المحافظة على ترتيب تسلسل المصدر للجزء المتبقي من الاستعلام، أو حتى ترتيب هو تغير، على سبيل المثال باستخدام جملة orderby (ترتيب حسب في Vlsual أساسى).

AsUnordered()

يحدد هذا PLINQ لبقية الاستعلام هو غير مطلوب للمحافظة على ترتيب التسلسل المصدر.

WithCancellation()

يحدد أنه يجب أن PLINQ مراقبة الولاية الرمز المميز المتوفر للإلغاء الأمر دورياً وإلغاء الأمر تنفيذ إذا أنه هو المطلوبة.

WithDegreeOfParallelism()

تعين الحد الأقصى لعدد المعالجات التي يجب أن تستخدم PLINQ إلى parallelize الاستعلام.

WithMergeOptions()

توفير تلميح حول كيف يجب أن PLINQ، إذا هو المحتملة، نتائج الدمج المتوازية إلى تسلسل واحد فقط تشغيل مؤشر ترابط كبيرا.

WithExecutionMode()

تحديد ما إذا كان يجب على PLINQ parallelize الاستعلام حتى عندما يكون سلوك الافتراضي هو إلى تشغيله بشكل تسلسلي.

ForAll()

أسلوب قائمة تعداد ذات مؤشرات ترابط متعددة تمكنك، التكرار عبر نتائج الاستعلام، بعكس النتائج للمعالجة في متوازى دون دمج اﻷول مرة أخرى إلى مسار التنفيذ مستهلك.

Aggregate()زيادة التحميل

التحميل الزائد الذي هو الفريدة الخاصة بالتجميع المتوسطة PLINQ وتمكن عبر أقسام مؤشر ترابط المحلية، بالإضافة إلى دالة تجميع نهائي لجمع نتائج الجميع الأقسام.

نموذج اشتراك

عندما تقوم بكتابة استعلام، عليك الحتمية إلى PLINQ قبل استدعاء ParallelEnumerableAsParallel()أسلوب التوسيع تشغيل مصدر بيانات، كما هو موضح في المثال التالي.

Dim source = Enumerable.Range(1, 10000)

' Opt in to PLINQ with AsParallel
Dim evenNums = From num In source.AsParallel()
               Where Compute(num) > 0
               Select num
var source = Enumerable.Range(1, 10000);


// Opt-in to PLINQ with AsParallel
var evenNums = from num in source.AsParallel()
               where Compute(num) > 0
               select num;

ParallelEnumerableAsParallel()أسلوب التوسيع الربط اللاحقة استعلام عوامل التشغيل، في هذه الحالة، whereو select، إلى System.Linq.ParallelEnumerableتطبيقات.

أوضاع التنفيذ

بشكل افتراضي، PLINQ هو المحافظة. في وقت التشغيل، البنية التحتية PLINQ بتحليل بنية الكلي استعلام. إذا كان الاستعلام هو المحتمل أن العائد speedups ب parallelization، PLINQ أقسام تسلسل المصدر في المهام التي يمكن تشغيلها بشكل متزامن. إذا كان ذلك هو غير آمنة استعلام parallelize، PLINQ فقط تشغيل الاستعلام بالتتابع. إذا كان PLINQ الاختيار بين يحتمل أن يكون مكلفاً متوازى خوارزمية أو خوارزمية متسلسلة غير مكلفة، اختار خوارزمية المتسلسلة بشكل افتراضي. يمكنك استخدام WithExecutionModeالأسلوب و System.Linq.ParallelExecutionModeالتعداد لإرشاد PLINQ لتحديد متوازى خوارزمية. ويكون هذا مفيداً إذا كنت تعرف بواسطة الاختبار والقياس الذي يقوم بتنفيذ استعلام معين بسرعة في نفس الوقت. لمزيد من المعلومات، راجع كيفية القيام بما يلي: قم بتحديد "الوضع" تنفيذ "في PLINQ.

درجة Parallelism

يستخدم بشكل افتراضي PLINQ الجميع المعالجات في الكمبيوتر مضيف إلى كحد أقصى 64. يمكن إرشاد PLINQ إلى استخدام لا المزيد عدد محدد من المعالجات باستخدام WithDegreeOfParallelism()الأسلوب. Th هو هو مفيداً عندما تريد التأكد من أن عمليات غير ذلك قيد التشغيل تشغيل جهاز الكمبيوتر بتلقي مقدار معين من وقت CPU. يحد المتكررة التالية الاستعلام إلى الاستفادة من المعالجات الثاني كحد أقصى.

Dim query = From item In source.AsParallel().WithDegreeOfParallelism(2)
            Where Compute(item) > 42
            Select item
var query = from item in source.AsParallel().WithDegreeOfParallelism(2)
            where Compute(item) > 42
            select item;

في الحالات الموقع يكون استعلام هو تنفيذ مقداراً كبيرا من العمل غير جهازك-المرتبطة مثل "ملف الادخال/الاخراج"، قد يكون مفيداً لتحديد درجة من parallelهوm أكبر من عدد أساسيات تشغيل آلة.

طلبها مقابل استعلامات متوازى غير مرتبة

في بعض الاستعلامات، يجب أن ينتج عامل تشغيل استعلام نتائج التي يتم الاحتفاظ بترتيب تسلسل المصدر. يوفر PLINQ ParallelEnumerableAsOrdered()عامل لهذا الغرض. AsOrdered()هو dهوtinct منAsSequential(). AsOrdered()تسلسل هو معالجتها باستمرار في نفس الوقت، ولكن يتم تخزينها مؤقتاً نتائجه وفرز. لأنه يتضمن بها ترتيب عادة بالعمل الإضافي AsOrdered()قد يتم معالجة تسلسل المزيد بطء من الافتراضي AsUnordered()التسلسل. ما إذا كان معينة بترتيب عملية متوازية هو أسرع من الإصدار العملية متسلسلة يعتمد تشغيل عوامل عديدة.

يلي تعليمات برمجية مثال يوضح كيفية الحتمية على ترتيب بها.

        Dim evenNums = From num In numbers.AsParallel().AsOrdered()
                      Where num Mod 2 = 0
                      Select num



            evenNums = from num in numbers.AsParallel().AsOrdered()
                       where num % 2 == 0
                       select num;


لمزيد من المعلومات، راجع ترتيب بها في PLINQ.

متوازى أو.استعلامات متتالية

تتطلب بعض العمليات تسليم بيانات المصدر بطريقة متسلسلة. ParallelEnumerableالاستعلام العوامل بالتحويل إلى الوضع متسلسلة تلقائياً عند فإنه هو المطلوبة. عوامل تشغيل استعلام المعرفة من قبل مستخدم ومستخدم المفوضون التي تتطلب التنفيذ متسلسلة، يوفر PLINQ AsSequential()الأسلوب. عندما تقوم باستخدام AsSequential()، يتم تنفيذ الجميع العوامل التالية في الاستعلام بالتتابع حتى AsParallel()هو يطلق مرة أخرى. لمزيد من المعلومات، راجع كيفية القيام بما يلي: يجمع متوازى واستعلامات LINQ التسلسلي.

خيارات لدمج نتائج استعلام

عند تنفيذ استعلام PLINQ في متوازى، يجب أن يتم دمج نتائجه من كل مؤشر ترابط العامل مرة أخرى إلى عملية جزئية الرئيسية استهلاك قبل foreachتكرار حلقي ( For Eachفي Visual Basic)، أو إدراجها في قائمة أو صفيفة. في بعض الحالات، قد يكون مفيداً إلى تحديد نوع معين من عملية الدمج، على سبيل المثال، إلى بدء إنتاج نتائج بسرعة أكبر. بالنسبة لهذا الغرض، يعتمد PLINQ WithParallelMergeOptions()أسلوب، و ParallelMergeOptionsالتعداد. لمزيد من المعلومات، راجع دمج خيارات في PLINQ.

عامل تشغيل ForAll

في متسلسلة LINQتنفيذ استعلامات هو تأجيلها حتى الاستعلام هو تعداد أما في تكرار حلقي foreach(For EachinVisual Basic) أو بواسطة استدعاء أسلوب مثل ToList، ToArray، أو ToDictionary. في PLINQ، كما يمكنك استخدام foreachإلى تنفيذ الاستعلام ويكرر من خلال نتائج. ومع ذلك، foreachنفسه لا يعمل في نفس الوقت، ولذلك، فإنه يتطلب أن الإخراج من الجميع المهام متوازي دمجها مرة أخرى في مؤشر ترابط الذي الحلقة هو قيد التشغيل. في PLINQ، يمكنك استخدام foreachعندما يجب الاحتفاظ بالترتيب النهائي لنتائج الاستعلام، و أيضا عند الذي يتم معالجة نتائج بطريقة تسلسلية، على سبيل المثال عند الذي تحاول الاتصال به Console.WriteLineلكل عنصر. لينفذ الاستعلام أسرع عند طلب بها هو غير مطلوبة وعند معالجة نتائج يمكن نفسه أن parallelized، استخدم ParallelEnumerableForAll()أسلوب لينفذ استعلام PLINQ. ForAllلا يقوم هذا خطوة الدمج النهائية. يظهر مثال التعليمة البرمجية التالية كيفية استخدام ForAll()الأسلوب.System.Collections.Concurrent.ConcurrentBag<T>هو المستخدم هنا لأن ذلك هو لمؤشرات ترابط متعددة بإضافة نفس الوقت دون محاولة إزالة أية عناصر.

Dim nums = Enumerable.Range(10, 10000)
Dim query = From num In nums.AsParallel()
            Where num Mod 10 = 0
            Select num

' Process the results as each thread completes
' and add them to a System.Collections.Concurrent.ConcurrentBag(Of Int)
' which can safely accept concurrent add operations
query.ForAll(Sub(e) concurrentBag.Add(Compute(e)))

var nums = Enumerable.Range(10, 10000);


var query = from num in nums.AsParallel()
            where num % 10 == 0
            select num;

// Process the results as each thread completes
// and add them to a System.Collections.Concurrent.ConcurrentBag(Of Int)
// which can safely accept concurrent add operations
query.ForAll((e) => concurrentBag.Add(Compute(e)));

يبين المثال التالي الفرق بين foreachو ForAllبالنظر إلى عن التنفيذ.

ForAll مقابل ForEach

الإلغاء

PLINQ هو بالتكامل مع أنواع الإلغاء في .NET Framework 4. لمزيد من المعلومات، راجع Cancellation. ولذلك، بعكس الاستعلامات LINQ إلى كائنات متسلسلة، استعلامات PLINQ يمكن أن يتم إلغاء. إلى إنشاء استعلام PLINQ cancelable، استخدم WithCancellation()operaإلىr على الاستعلام وتوفير CancellationTokenمثيل كوسيطة. عند IsCancellationRequestedخاصية تشغيل الرمز المميز هو التعيين إلى القيمة صواب، PLINQ سوف تلاحظ أنه إيقاف معالجة تشغيل الجميع عمليات جزئية وقم بطرح OperationCancelledException.

هو المحتملة التي قد تستمر استعلام PLINQ لمعالجة بعض العناصر بعد الرمز المميز للإلغاء هو تعيين.

استجابة أكبر، يمكنك أيضا الرد إلى طلبات الإلغاء في تفويضات مستخدم تشغيلها لفترة طويلة. لمزيد من المعلومات، راجع كيفية القيام بما يلي: قم بإلغاء استعلام PLINQ.

Exceptions

عند تنفيذ استعلام PLINQ، استثناءات متعددة قد تكون طرح من عمليات جزئية المختلفة في نفس الوقت. أيضا، التعليمة البرمجية لمعالجة excepti تشغيل قد تشغيل مؤشر ترابط مختلف من تعليمات برمجية التي قام بإلقاء excepti تشغيل. يستخدم PLINQ AggregateExceptionنوع تغليف الجميع الاستثناءات التي تم طرح بواسطة استعلام، وتنظيم هذه الاستثناءات إلى مؤشر ترابط استدعاء. في مؤشر ترابط استدعاء، مطلوب حظر المحاولة catch واحد فقط. ومع ذلك، يمكنك يكرر خلال الجميع الاستثناءات التي يتم تغليف في AggregateExceptionو التقاط أي يمكنك استرد من بشكل اﻷمن. في بعض الحالات النادرة، بعض الاستثناءات قد تكون طرح التي يتم التفاف غير AggregateException، كما يتم التفاف و ThreadAbortExceptions لا.

عندما مسموح ب‏‏ استثناءات فقاعي للخلف لمؤشر ترابط ضم، ومن ثم هو المحتملة التي قد يستمر استعلام لمعالجة بعض عناصر بعد ‏‏ استثناء هو raهوed.

لمزيد من المعلومات، راجع كيفية القيام بما يلي: استثناءات مؤشر في استعلام PLINQ.

Partitioners مخصص

في بعض الحالات، يمكنك تحسين أداء الاستعلام بكتابة partitioner مخصصة التي تستفيد من بعض صفة مميزة المصدر بيانات. في استعلام، partitioner المخصص نفسه هو قابل للتعداد الكائن الذي تم الاستعلام عنه.

[Visual Basic]
Dim arr(10000) As Integer
Dim partitioner = New MyArrayPartitioner(Of Integer)(arr)
Dim query = partitioner.AsParallel().Select(Function(x) SomeFunction(x))

[C#]
int[] arr= ...;
Partitioner<int> partitioner = newMyArrayPartitioner<int>(arr);
var q = partitioner.AsParallel().Select(x => SomeFunction(x));

PLINQ يعتمد على عدد ثابت من الأقسام (بالرغم من أن إعادة بيانات قد يكون حيويا تعيين إلى هذه الأقسام أثناء وقت التشغيل لموازنة تحميل.). For() and ParallelForEach() support only dynamic partitioning, which means that the number of partitions changes at run time. لمزيد من المعلومات، راجع مخصص Partitioners PLINQ و TPL.

قياس الأداء PLINQ

في كثير من الحالات، يمكن أن يكون استعلام متوازى ized، ولكن مقدار الحمل لإعداد متوازى outweighs الاستعلام gained من الفائدة للأداء. إذا لا يقوم استعلام لحساب مقدار أو مصدر بيانات هو صغيرة، استعلام PLINQ قد تكون أبطأ من LINQ متسلسلة للاستعلام عن الكائنات. يمكنك استخدام "محلل الأداء متوازٍ" في خادم فريق Studio Vهوual لمقارنة أداء استعلامات مختلفة لتحديد الاختناقات المعالجة، ولتحديد ما إذا كان الاستعلام الخاص بك هو قيد التشغيل بالتوازي أو بالتتابع. للمزيد من المعلومات، راجع طرق عرض البيانات في تنفيذ مؤشر الترابط وكيفية القيام بما يلي: المقياس الأداء PLINQ على الاستعلام.

راجع أيضًا:

المبادئ

متوازى LINQ (PLINQ)

موارد أخرى

فهم زيادةالسرعة في PLINQ