並列プログラミングと並行プログラミングの違いは?


44

並行プログラミングを見るとき、2つの用語、つまり並行と並列が一般的に使用されます。

また、一部のプログラミング言語は、Javaなどの並列プログラミングのサポートを明確に主張しています

これは、並列プログラミングと並行プログラミングが実際に異なることを意味しますか?


10
はい、同時プログラミングと並列プログラミングは異なります。たとえば、コンテキストスイッチングを介して、同じコアで2つのスレッド(またはプロセス)を同時に実行できます。2つのスレッド(またはプロセス)を2つの異なるコア(またはプロセッサ)で実行すると、並列性が得られます。したがって、前者の場合(並行性)の並列処理は「仮想」のみですが、後者の場合は真の並列処理が可能です。したがって、すべての並列プログラムは同時に実行されますが、その逆は必ずしも当てはまりません。
マッシモカファロ14年

1
ここで注意してください。言語サポート(つまり、新しいコンストラクトで言語を拡張する)または低レベルのアプローチ(MPIやOpenMPの場合のようにライブラリを使用するなど)を使用して、同じ結果を達成できます。とにかく、現在のマルチコアプロセッサとSMPサポートを備えたオペレーティングシステムでは、OSが異なるコアでプログラムの実行のスレッドをスケジュールする場合、古いシングルコアプロセッサで実行する場合に並行するプログラムを並行して実行できます。そのため、この区別は最近では少し「ぼやけ」ています。
マッシモカファロ14年

3
一定の光遅延速度に使用するもの。並行性では、光遅延の速度は1クロックサイクルのふりをします。並行して、1つのサーバーが隣にあると想定し、分散では、1つのサーバーが火星にあると想定します。


1
Robert Harperは、この問題について2つのブログ投稿で説明しています。「並行性は並行性ではありません」「平行性と並行性、再訪」です。
バジル14年

回答:


26

並列性(単位時間あたりにより多くの作業を行うために追加の計算ユニットを使用)と同時実行(共有リソースへのアクセスの管理)を区別します。並列性を最初に教えるのは、それが簡単で、非シーケンシャルな考え方を確立するのに役立つからです。

Dan Grossman著「A Sophomoric ∗ Introduction to Shared Memory Parallelism and Concurrency」(2013年11月16日版)より


21

Nishの答えに加えて、Haskellの並列および並行プログラミングに関するSimon Marlowの本または彼の短いチュートリアルをお勧めします。Haskellの観点からあなたの最初の質問に答えてくれるので、理論的に傾いた読者により適している可能性があります(Haskellは純粋に機能的で怠zyなプログラミング言語で、他の言語よりも数学にずっと近いです)。

そこから引用:

多くの分野で、パラレルとコンカレントという言葉は同義語です。基本的に異なる概念を記述するために使用されるプログラミングではそうではありません。

並列プログラムは、計算をより高速に実行するために、多数の計算ハードウェア(複数のプロセッサコアなど)を使用するプログラムです。計算の異なる部分は、同時に(並列に)実行される異なるプロセッサに委任されるため、結果は、計算が連続して実行された場合よりも早く配信される可能性があります。

対照的に、並行性は、制御の複数のスレッドが存在するプログラム構造化手法です。概念的には、制御のスレッドは「同時に」実行されます。つまり、ユーザーには効果が交互に表示されます。実際に同時に実行するかどうかは、実装の詳細です。並行プログラムは、インターリーブ実行を介して単一のプロセッサで実行することも、複数の物理プロセッサで実行することもできます。

チュートリアル(p.4)の残りの部分を読むことをお勧めしますが、このセクションの残りの部分を引用します。これは、プログラミングパラダイムを、効率、モジュール性、決定性などのプログラムの定量的および定性的特性に結び付けているためです。

並列プログラミングは効率にのみ関係しますが、並行プログラミングは複数の独立した外部エージェント(ユーザー、データベースサーバー、一部の外部クライアントなど)と対話する必要があるプログラムの構造に関係します。並行性により、このようなプログラムをモジュール化できます。ユーザーと対話するスレッドは、データベースと通信するスレッドとは異なります。並行性がない場合、そのようなプログラムはイベントループとコールバックを使用して作成する必要があります-実際、多くの言語では並行性が高すぎるか、または難しすぎるため、並行性が利用可能な場合でもイベントループとコールバックがよく使用されますつかいます。

「制御のスレッド」の概念は、純粋に機能的なプログラムでは意味がありません。観察する効果がなく、評価の順序は無関係であるためです。したがって、並行性は、効果的なコードの構造化手法です。Haskellでは、これはIOモナドのコードを意味します。

関連する区別は、決定的プログラミングモデルと非決定的プログラミングモデルの違いです。決定論的プログラミングモデルは、各プログラムが1つの結果のみを提供できるモデルです。一方、非決定論的プログラミングモデルは、実行のいくつかの側面に応じて異なる結果をもたらす可能性があるプログラムを受け入れます。同時プログラミングモデルは、予測不可能な時間にイベントを発生させる外部エージェントと対話する必要があるため、必ずしも非決定的です。ただし、非決定性にはいくつかの顕著な欠点があります。プログラムのテストと推論が著しく難しくなります。

並列プログラミングの場合、可能な限り決定論的プログラミングモデルを使用します。目標は、より迅速に答えに到達することであるため、プロセスでデバッグを難しくすることは避けたいです。決定論的並列プログラミングは、両方の長所です。テスト、デバッグ、推論はシーケンシャルプログラムで実行できますが、プロセッサを追加するとプログラムが高速に実行されます。実際、ほとんどのコンピュータープロセッサ自体は、パイプライン化と複数の実行ユニットの形で決定論的な並列処理を実装しています。

並行性を使用して並列プログラミングを実行することは可能ですが、並行性は決定性を犠牲にするため、これは多くの場合不適切な選択です。Haskellでは、並列プログラミングモデルは決定論的です。ただし、決定論的プログラミングモデルでは、あらゆる種類の並列アルゴリズムを表現するには不十分であることに注意することが重要です。内部の非決定性に依存するアルゴリズム、特にソリューション空間の検索を伴う問題があります。Haskellでは、このクラスのアルゴリズムは並行性を使用してのみ表現できます。


20

並行性と並列性は、解決および引き起こす問題が異なりますが、独立しているわけではありません。

並行性

2つのタスクを同時に実行すると、両方のタスクの個々のステップがインターリーブ方式で実行されます。並列性を無視すると、ある時点で実行されるステートメントは1つだけであると想定できますが、次のステップを実行するタスクは(事前に)保証されません。

これはいくつかの点で役立ちます。

  • 1つのプログラムでの独立したタスクの明確なプログラミング。
  • 計算中にIOを処理できます(GUIなど)。
  • 一度に複数のプログラムを実行できます(OSレベルでの同時実行)。

主な課題は次のとおりです。

  • データの一貫性を維持します。
  • デッドロックライブロックを避けてください。
  • 並行プロセスの正確なセマンティクスを決定します。
  • 正確性を確保する静的プロパティを決定します。

並列処理

2つのタスクを並行して実行すると、ステートメントが同時に実行さます。これは主に次の場合に役立ちます。

  • プログラムを並列実行することにより、システムのスループットを改善します(例:マルチコアシステム)。
  • 一度に複数のCPUを利用することにより、個々のプログラムの実行時間を改善します。
  • 多くのマシン(例:分散データベース)でIOを使用します。

主な課題は次のとおりです。

  • 並列処理を使用できるアルゴリズムを許可および開発するパーティションの問題。
  • 計算ユニット間の依存関係と通信を最小限に抑えます。
  • 並行性によってもたらされるすべての問題:少なくともメモリの観点から見ると、並列プログラムはメモリアクセスのシリアル化のために並行プログラムのように見えます。
  • 最適でないハードウェアサポートに対処する。

並列コンピューティングと分散コンピューティングの区別については、この質問も参照してください。


5

少し理想的な答え、おそらく...

  • 並行性は、プログラムの作成方法のプロパティです。フォーク/結合、ロック、トランザクション、アトミックな比較とスワップ操作などの構造を使用してプログラムが記述されている場合、それは並行です。

  • 並列処理は、プログラムの実行方法のプロパティです。プログラムが複数の計算ユニットで同時に実行される場合、プログラムは並行して実行されています。


1

これにはたくさんの答えがありますが、混乱を招く可能性があります。私はそれをこのように考えるのが好きで、多分それは役立ちますか?:

並行プログラミングは、実行順序を気にしないコードです。Javaは並行プログラミングには不十分な言語ですが、役立つライブラリとフレームワークがあります。JavaScriptは並行プログラミングに最適な言語であり、並行していないものを書きたい場合(実行順序を強制したい場合など)に難しいことがよくあります。並行プログラミングは、イベントドリブンプログラミングに最適です(実行順序は、ボタンをクリックするか、ボックスに入力するときにブラウザーで実行されるコードのように、イベントリスナーによって決定されます)。

例には、100個のHTTP要求の作成が含まれます。NodeJSの最も簡単な解決策は、コールバックメソッドを使用して100リクエストすべてを一度に開き、応答が返されると毎回メソッドが実行されることです。それは並行プログラミングです。Rubyでは、最も単純な(最も一般的な)ソリューションは、リクエストを開いてレスポンスを処理する、次のリクエストを開いてレスポンスを処理するなどです。サーバーに打撃を与えたり、アウトバウンド接続を制限したりしないように注意してください(誤って簡単に実行できます)。Rubyを並行して作成することはできますが、ほとんどのRubyコードがどのように作成されるかではなく、それを行うのは少し痛いです。

並列プログラミング複数のスレッドまたはプロセスで同時に実行できるコードです。これにより、複数のCPUでコードを実行することでパフォーマンスを最適化することができます(Akkaのように、多くの場合、複数のマシンが含まれます)。NodeJSはマルチスレッドではないため、並列実行がないため、スレッドセーフコードの記述について心配する必要はありません(そして、私が見たほとんどのJavaScriptコードはスレッドセーフではありません)。Javaでは、言語が並行プログラミングを通常のパターンにしない場合でも、並列プログラミングは非常に組み込まれているため、多くの場合、スレッドの安全性について心配する必要があります。JavaでWebサイトを作成する場合、通常、これは同じメモリ内の個別のスレッドで各リクエストを実行するコンテナで実行されます。


上記のいくつかは、あなたが話している範囲と境界に依存します。私はウェブサイトで働いています。私が見るほとんどのJavaコードは並行プログラミングではありません。もちろん、十分にズームアウトすれば、顧客が要求する順序は重要ではありませんが、それ以上ズームインすると、実行される順序はコードによって決まります。ただし、コードは、要求がスレッドセーフでなければならない多くの共有オブジェクトと並行して実行できるように記述されています。

一方、私が見るほとんどのJavaScriptコードは並行しています。多くのレベルで実行順序が重要でないように書かれています。ただし、共有メモリでの並列実行をサポートするようには書かれていません。もちろん、複数のプロセスで同じコードを並列に実行できますが、オブジェクトは共有されないため、意味のある並列プログラミングではありません。

さらに読むために、私はここでこの質問に対するトップアンサーのイラストが本当に好きです:https : //www.quora.com/What-are-the-differences-between-parallel-concurrent-and-asynchronous-programming

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.