問題タブ [concurrent-collections]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
.net - BlockingCollection を使用してファイルを別のファイルにコピーします。宛先はソースとは異なり、場合によってはガベージです。コードで何か見落としていますか?
編集と更新 -私は自分のパソコンで同じコードを試してみましたが、非常にうまく動作します。この同じコードを使用して、問題なく任意のタイプのファイルをコピーできました。仕事用のコンピューターでコードを実行すると、この問題が発生します。これがどのように、そしてなぜこれがコンピューターに依存するのか理解できません。ここで何か不足しているかどうか教えてください。
readTask では、ファイルを順次読み取り、そのバイトを BlockingCollection に追加しています。そして消費タスクでは、BlockingCollection に表示されるデータを読み取り、ファイルに書き込みます。デフォルトでは、BlockingCollection は ConcurrentQueue のラッパーであるため、ブロッキング キューからの読み取りは、書き込まれた順序と同じになると予想されます。しかし、宛先ファイルをソースと比較すると、まったく異なり、重複が見られることがあります。
私のソースファイルは、以下のように、各番号が新しい行にある一連の番号です。
私のファイルには、ファイルに十分なサイズを持たせるために約5000個の数字があります。このコードに何か問題がありますか? または、コレクションのブロックが機能するはずの方法ではありません。この例ではファイルに書き込んでいますが、実際にはこのファイルを Rest API にプッシュする必要があり、データが順番に送信されることが重要です。バイトを順番に送信できない場合、ファイルはサーバーに保存されたときに破損します。
c# - 頻繁な読み取り操作とまれな書き込み操作に使用する同時収集 (.NET)
Web アプリケーションにキャッシュを作成したいと考えています。これにより、最上位層 (MVC) が、下位層 (サービスと DB) から取得した値を永続化して、不要な要求を回避できるようになります。キャッシュに保存したいデータは Web サイトのすべてのページで必要になるため、このキャッシュはリクエストの量を大幅に削減することを目的としています。アイデアは、多くのスレッドがコレクションからデータを読み取り、1 つのスレッドがそれをクリアして、キャッシュの有効期限が切れた後に新しいデータを取得するというものです。これは、コレクションが頻繁な読み取り操作とまれな書き込み操作に使用されることを意味します。
私にとっての問題は、これらの目的に適したクラスを選択することです。.NET 4 で導入されたからの同時実行クラスのセットについて読みました。またはSystem.Collections.Concurrent
を使用する必要はまったくありませんが、とのいずれかを選択する必要があります。 ConcurrentQueue
ConcurrentStack
BlockingCollection
ConcurrentBag
ConcurrentDictionary
ConcurrentBag
この場合の最良の解決策のようです。しかし、私はこの記事でその並行辞書を読みました
...読み取り操作では完全にロックフリーです。このように、辞書からの読み取りが最も頻繁な操作であるシナリオに最適化されています。
おそらく最善の解決策は、ConcurrentDictionary<int, MyTypeOfObj>
代わりに使用することですか?それとも、私は並行型をまったく必要とせず、単純List
に仕事をするのでしょうか? おそらく、キャッシュの更新時に操作をロックすることができれば、それでよいでしょう。しかし、 simple を使用することlock
は望ましくありません。
アドバイスや説明をいただければ幸いです。
アップデート
キャッシュは、アウトレットのマップ ポイントを格納するために使用されます。アウトレットのセットは非常に安定していますが、それらを追加するための UI があるはずなので、挿入操作は非常にまれです。タイムアウト後に基になるレイヤーからコレクション全体を取得し、挿入操作を実行する方が簡単な場合があります。検索も必要ありません。読み取りは単純な列挙を意味します。
c# - アクセスパターンが好ましくないことがわかっている場合でも、ConcurrentBag はオブジェクトプールをバッキングするための適切な選択ですか?
プロファイリングを行った後、アプリケーション内の特定のオブジェクトは、オブジェクト プールを作成する代わりに使用することで大きなメリットがあることがわかりました。このアプリケーションは、複数のスレッドを持つプロデューサー/コンシューマー キューに基づいています。
ConcurrentBag コレクションは基本的に ObjectPool であり、アプリケーションのオブジェクト プールのバッキング ストアとして最適なようです。私が正しく理解していれば、ConcurrentBag は概念的に次のように機能します。
- バギングされたオブジェクトの ThreadLocal コレクションを保持します。挿入する場合はこのコレクションに追加し、削除する場合はこのコレクションから削除します。
- ローカル コレクションに要素がなく、オブジェクトを削除する必要がある場合は、別のスレッドのローカル コレクションから 1 つ盗みます。
問題は、アプリケーションが常にスレッド 'A' でオブジェクトを要求し、常にスレッド 'B' でそれを返すことを既に知っていることです。したがって、常にスチール ケースがデフォルトになります。
このアクセス パターンを知っている場合、フレームワークによって提供される別のコレクションを使用してオブジェクト プールをバックアップする方がよいでしょうか?
c# - 並行コレクションの継承/カプセル化 c#
ConcurrentDictionary をカプセル化するカスタム コレクションを作成しています。一般的なコレクションからのカプセル化/継承に関する多くの情報を見つけましたが、並行コレクションに固有のものは何も見つかりませんでした。これは私の基本ケースのコード スニペットであり、その後にいくつかの一般的な質問が続きます。
- この方法で並行コレクションをカプセル化することは許容されますか? それとも、ジェネリック コレクションから独自のスレッド セーフ コレクションを作成する領域に移行するのでしょうか?
- カスタム コレクションはスレッドセーフですか?
- 並行コレクションの継承は受け入れられますか? そうであれば、非並行コレクションから継承するためのこれ
class ItemCollection : ConcurrentDictionary<string, Item>
に似た、いくつかのガイドラインは何ですか。 - Select のようなメソッドの転送メソッドをどのように実装しますか? 次のような一連のバリエーションを試しましたが、機能しません。
public IEnumerable<TResult> Select<ItemCollection, TResult>(this ItemCollection source, Func<KeyValuePair<string, Item>, TResult> selector) { return Collection.Select(selector); }
ConcurrentDictionary を継承すると、次のような実装になります
c# - ConcurrentDictionary でタスクを使用する方法
データベースからキューを読み取って処理するプログラムを作成する必要があり、すべてのキューは並行して実行され、ConcurrentDictionary を使用して親スレッドで管理されます。キューを表すクラスがあります。このクラスには、キュー情報と親インスタンス ハンドルを受け取るコンストラクターがあります。キュー クラスには、キューを処理するメソッドもあります。
キュー クラスは次のとおりです。
親スレッドはキューのデータセットをループし、新しいキュー クラスをインスタンス化します。Queue オブジェクトの Process メソッドを非同期的に実行する新しいスレッドを生成します。このスレッドは ConcurrentDictionary に追加され、次のように開始されます。
これは非同期キュー処理を管理するための正しいアプローチではないと感じています。この設計でデッドロックが発生する可能性があるのではないかと考えています。さらに、タスクを使用して、新しいスレッドの代わりにキューを非同期で実行したいと考えています。前の実行がまだ完了していない場合、同じキューに対して新しいスレッドまたはタスクを生成しないため、キューを追跡する必要があります。このタイプの並列処理を処理する最良の方法は何ですか?
前もって感謝します!
c# - 通常のコレクション .net を含む同時コレクション
私が持っているとしましょうConcurrentDictionary<int, HashSet<int>> sampleCollection;
。操作を実行するのはスレッドセーフですかsampleCollection[1]
(これはHashSet<int>
)?
一般に、スレッド セーフなコレクション内にスレッド セーフでないコレクションがある場合、スレッド セーフでないコレクションをスレッド セーフな外側のコレクションから操作するのはスレッド セーフですか?
.net - なぜ BlockingCollection はICollection を実装しない?
現在の実装は次のようになります。
なぜそれが実装されないのか、誰にも分かりますICollection<T>
か? なんか面倒くさい…