Sdílet prostřednictvím


Přehled Concurrency Runtime

Tento dokument obsahuje přehled modulu Concurrency Runtime. Popisuje výhody modulu Concurrency Runtime, kdy ho používat a jak spolu její komponenty spolupracují a s operačním systémem a aplikacemi.

Oddíly

Tento dokument obsahuje následující části:

Historie implementace modulu Concurrency Runtime

V sadě Visual Studio 2010 až 2013 byl modul Concurrency Runtime začleněn do msvcr100.dll prostřednictvím msvcr120.dll. Při refaktoringu UCRT v sadě Visual Studio 2015 došlo k refaktoringu knihovny DLL do tří částí:

  • ucrtbase.dll – rozhraní C API, dodáváno ve Windows 10 a obsluhováno na nižší úrovni prostřednictvím služba Windows Update-

  • vcruntime140.dll – Funkce podpory kompilátoru a modul runtime EH dodávané přes Visual Studio

  • concrt140.dll – Concurrency Runtime, dodáno prostřednictvím sady Visual Studio. Vyžadováno pro paralelní kontejnery a algoritmy, například concurrency::parallel_for. STL také vyžaduje tuto knihovnu DLL v systému Windows XP pro primitivy synchronizace napájení, protože systém Windows XP nemá proměnné podmínky.

V sadě Visual Studio 2015 a novějším už plánovač úloh Concurrency Runtime není plánovačem pro třídu úloh a související typy v ppltasks.h. Tyto typy nyní používají Fond vláken systému Windows pro lepší výkon a interoperabilitu s primitivami synchronizace Windows.

Proč je modul runtime pro souběžnost důležitý

Modul runtime pro souběžnost poskytuje jednotnost a předvídatelnost aplikací a komponent aplikace, které běží současně. Dva příklady výhod modulu Concurrency Runtime jsou kooperativní plánování úkolů a blokování spolupráce.

Modul Concurrency Runtime používá plánovač úloh spolupráce, který implementuje algoritmus krádeže práce, který efektivně distribuuje práci mezi výpočetní prostředky. Představte si například aplikaci, která má dvě vlákna spravovaná stejným modulem runtime. Pokud jedno vlákno dokončí naplánovanou úlohu, může přesměrovat práci z druhého vlákna. Tento mechanismus vyrovnává celkovou úlohu aplikace.

Concurrency Runtime také poskytuje primitivy synchronizace, které používají kooperativní blokování k synchronizaci přístupu k prostředkům. Představte si například úkol, který musí mít výhradní přístup ke sdílenému zdroji. Když modul runtime blokuje spolupráci, může zbývající kvantový modul použít k provedení jiné úlohy, protože první úkol čeká na prostředek. Tento mechanismus podporuje maximální využití výpočetních prostředků.

[Nahoře]

Architektura

Modul Concurrency Runtime je rozdělený do čtyř komponent: knihovna PPL (Parallel Patterns Library), asynchronní knihovna agentů, plánovač úloh a Resource Manager. Tyto komponenty se nacházejí mezi operačním systémem a aplikacemi. Následující obrázek ukazuje, jak komponenty Concurrency Runtime komunikují mezi operačním systémem a aplikacemi:

Architektura concurrency Runtime

Architektura modulu Concurrency Runtime.

Důležité

Komponenty Plánovač úloh a Resource Manager nejsou k dispozici z aplikace Univerzální platforma Windows (UPW) nebo při použití třídy úloh nebo jiných typů v ppltasks.h.

Concurrency Runtime je vysoce kompozovatelný, to znamená, že můžete zkombinovat stávající funkce, abyste mohli dělat více. Concurrency Runtime skládá mnoho funkcí, jako jsou paralelní algoritmy, z komponent nižší úrovně.

Concurrency Runtime také poskytuje primitivy synchronizace, které používají kooperativní blokování k synchronizaci přístupu k prostředkům. Další informace o těchto primitivách synchronizace naleznete v tématu Synchronizační datové struktury.

V následujících částech najdete stručný přehled toho, co jednotlivé komponenty poskytují a kdy ji používat.

Knihovna PPL (Parallel Patterns Library)

Knihovna PPL (Parallel Patterns Library) poskytuje kontejnery a algoritmy pro obecné účely pro provádění jemně odstupňovaného paralelismu. PPL umožňuje imperativní datový paralelismus tím, že poskytuje paralelní algoritmy, které distribuují výpočty v kolekcích nebo sadách dat napříč výpočetními prostředky. Umožňuje také paralelismus úkolů tím, že poskytuje objekty úkolů, které distribuují více nezávislých operací mezi výpočetní prostředky.

Knihovnu paralelních vzorů použijte, pokud máte místní výpočet, který může těžit z paralelního provádění. Můžete například použít algoritmus concurrency::p arallel_for k transformaci existující for smyčky tak, aby fungoval paralelně.

Další informace o knihovně paralelních vzorů naleznete v tématu Knihovna PPL (Parallel Patterns Library).

Knihovna asynchronních agentů

Knihovna asynchronních agentů (nebo jen Knihovna agentů) poskytuje programovací model založený na objektech actor i rozhraní pro předávání zpráv pro hrubě odstupňované úlohy toku dat a kanálování. Asynchronní agenti umožňují produktivní využití latence provedením práce jako ostatní komponenty čekají na data.

Knihovnu agentů použijte, pokud máte více entit, které vzájemně komunikují asynchronně. Můžete například vytvořit agenta, který čte data ze souboru nebo síťového připojení a pak pomocí rozhraní pro předávání zpráv odešle tato data jinému agentu.

Další informace o knihovně agentů najdete v tématu Knihovna asynchronních agentů.

Plánovač úloh

Plánovač úloh plánuje a koordinuje úkoly za běhu. Plánovač úloh spolupracuje a využívá algoritmus krádeže práce k dosažení maximálního využití prostředků zpracování.

Modul Concurrency Runtime poskytuje výchozí plánovač, takže nemusíte spravovat podrobnosti o infrastruktuře. Pokud ale chcete splnit požadavky vaší aplikace na kvalitu, můžete také poskytnout vlastní zásady plánování nebo přidružit konkrétní plánovače ke konkrétním úkolům.

Další informace o plánovači úloh naleznete v tématu Plánovač úloh.

Správce zdrojů

Role Resource Manageru je spravovat výpočetní prostředky, jako jsou procesory a paměť. Resource Manager reaguje na úlohy, když se mění v době běhu tím, že přiřazuje prostředky tam, kde můžou být nejúčinnější.

Resource Manager slouží jako abstrakce nad výpočetními prostředky a primárně komunikuje s plánovačem úloh. I když můžete Pomocí Resource Manageru doladit výkon knihoven a aplikací, obvykle používáte funkce poskytované knihovnou paralelních vzorů, knihovnou agentů a plánovačem úloh. Tyto knihovny používají Resource Manager k dynamickému obnovení rovnováhy prostředků při změně úloh.

[Nahoře]

Výrazy lambda jazyka C++

Mnoho typů a algoritmů definovaných modulem Concurrency Runtime se implementuje jako šablony jazyka C++. Některé z těchto typů a algoritmů berou jako parametr rutinu, která provádí práci. Tento parametr může být funkce lambda, objekt funkce nebo ukazatel funkce. Tyto entity se také označují jako pracovní funkce nebo pracovní rutiny.

Výrazy lambda jsou důležitou novou funkcí jazyka Visual C++, protože poskytují stručný způsob, jak definovat pracovní funkce pro paralelní zpracování. Objekty funkcí a ukazatele na funkce umožňují používat Concurrency Runtime s existujícím kódem. Při psaní nového kódu ale doporučujeme používat výrazy lambda z důvodu bezpečnostních a produktivních výhod, které poskytují.

Následující příklad porovnává syntaxi funkcí lambda, objektů funkcí a ukazatelů funkce ve více voláních souběžnosti::p arallel_for_each algoritmu. Každé volání parallel_for_each používá jinou techniku výpočtu čtverce každého prvku v objektu std::array .

// comparing-work-functions.cpp
// compile with: /EHsc
#include <ppl.h>
#include <array>
#include <iostream>

using namespace concurrency;
using namespace std;

// Function object (functor) class that computes the square of its input.
template<class Ty>
class SquareFunctor
{
public:
   void operator()(Ty& n) const
   {
      n *= n;
   }
};

// Function that computes the square of its input.
template<class Ty>
void square_function(Ty& n)
{
   n *= n;
}

int wmain()
{
   // Create an array object that contains 5 values.
   array<int, 5> values = { 1, 2, 3, 4, 5 };

   // Use a lambda function, a function object, and a function pointer to 
   // compute the square of each element of the array in parallel.

   // Use a lambda function to square each element.
   parallel_for_each(begin(values), end(values), [](int& n){n *= n;});

   // Use a function object (functor) to square each element.
   parallel_for_each(begin(values), end(values), SquareFunctor<int>());

   // Use a function pointer to square each element.
   parallel_for_each(begin(values), end(values), &square_function<int>);

   // Print each element of the array to the console.
   for_each(begin(values), end(values), [](int& n) { 
      wcout << n << endl;
   });
}

Výstup

1
256
6561
65536
390625

Další informace o funkcích lambda v jazyce C++ najdete v tématu Výrazy lambda.

[Nahoře]

Požadavky

Následující tabulka ukazuje soubory hlaviček, které jsou přidružené ke každé komponentě Concurrency Runtime:

Komponenta Soubory hlaviček
Knihovna PPL (Parallel Patterns Library) ppl.h

concurrent_queue.h

concurrent_vector.h
Knihovna asynchronních agentů agents.h
Plánovač úloh concrt.h
Správce zdrojů concrtrm.h

Concurrency Runtime je deklarován v oboru názvů Concurrency . (Můžete také použít souběžnost, což je alias pro tento obor názvů.) Obor concurrency::details názvů podporuje architekturu Concurrency Runtime a není určená k použití přímo z vašeho kódu.

Concurrency Runtime se poskytuje jako součást knihovny C Runtime (CRT). Další informace o tom, jak vytvořit aplikaci, která používá CRT, naleznete v tématu Funkce knihovny CRT.

[Nahoře]