F# Asynchronous Workflows with the Coordination and Concurrency Runtime
F# ships with library support for ‘mailboxes’, an asynchronous message-passing mechanism recently popularised by interest in Erlang. This is good news. Message-passing in concurrent systems is always a saner approach than explicitly spawning threads and taking locks, and F#’s support for immutable types and values provides additional safety. Combined with the asynchronous workflows that the language also supports, a powerful Actor-oriented programming model is available to F# developers.
If you’re playing in this space in .Net though, I still think you can’t go past the Concurrency and Coordination Runtime (CCR), especially on performance terms, and it turns out to be straightforward to integrate the CCR with F# asynchronous workflows.
Let’s start out by defining some basic CCR support – this is mostly just plumbing…
#light
namespace FSharp.Ccr.Adaptors
open System
open System.Threading
open Microsoft.Ccr.Core
open Microsoft.Ccr.Core.Arbiters
type Receive() =
static let taskQueue = new DispatcherQueue()
static member internal TaskQueue with get() = taskQueue
static member internal activate(task : ITask) =
Arbiter.Activate(taskQueue, [| task |])
In the declaration above, there is only one task queue over the standard CLR thread-pool. I’ll cover the support for specifiable task queues in a later post. Now let’s cover some adaptor code that enables the use of the basic arbiters from within F# asynchronous workflows...
(* Receive. This allows us to write an asynchronous workflow that waits (but does not block)
on the port as follows:
let recv (port : Port<string>) =
async {
let! item = Receive.from port
printfn "%s" item
}
*)
[<OverloadID("from")>]
static member from (p : Port<'a>) =
Async.Primitive(fun (cont, econt) ->
Arbiter.Receive(false, p, (fun result -> cont result))
|> Receive.activate)
(* JoinedReceive. This allows us to write an asynchronous workflow that waits (but does not block)
until both ports have an item for processing. It then returns both in a tuple:
let recv (p1 : Port<string>, p2 : Port<int>) =
async {
let! s1,i1 = Receive.from_both (p1,p2)
printfn "%s %i" s1 i1
}
*)
[<OverloadID("from_both")>]
static member from_both (p1 : Port<'a>, p2 : Port<'b>) =
Async.Primitive(fun (cont, econt) ->
Arbiter.JoinedReceive(false, p1, p2, fun a b -> cont (a,b))
|> Receive.activate)
(* Choice. This allows us to write an asynchronous workflow that waits (but does not block)
until either port has an item for processing. It then returns the result in a
Choice:
let recv (p : PortSet<string,int>) =
async {
let! result = Receive.from_either p
match result with
| Choice2_1 s -> printfn "%s" s
| Choice2_2 i -> printfn "%i" i
}
*)
[<OverloadID("from_either")>]
static member from_either (ps : PortSet<'a,'b>) =
Async.Primitive(fun (cont, econt) ->
Arbiter.Choice(ps, (fun s -> cont (Choice2_1 s)), (fun e -> cont (Choice2_2 e)))
|> Receive.activate)
(* MultipleItemReceive. This allows us to write an asynchronous workflow that waits (but does not block)
until n items have queued to the port. It then returns the result in an array.
let recv (p : Port<string>) =
async {
let! result = Receive.multiple_from (p,100)
printfn "%i items received." result.Length
}
*)
[<OverloadID("multiple_from")>]
static member multiple_from (p : Port<'a>, n : int) =
Async.Primitive(fun (cont, econt) ->
Arbiter.MultipleItemReceive(false, p, n, fun r -> cont r)
|> Receive.activate)
(* MultipleItemReceive. This allows us to write an asynchronous workflow that waits (but does not block)
until n items have queued to the portset. It then returns the result as a tuple of
collections.
let recv (p : PortSet<string,Exception>) =
async {
let! results,failures = Receive.multiple_from_both (p,100)
printfn "%i results received and %i failures." results.Count failures.Count
}
*)
[<OverloadID("multiple_from_both")>]
static member multiple_from_both (p : PortSet<'a,'b>, n : int) =
Async.Primitive(fun (cont, econt) ->
Arbiter.MultipleItemReceive(p, n, fun f s -> cont (f,s))
|> Receive.activate)
(* MultiplePortReceive. This allows us to write an asynchronous workflow that waits (but does not block)
until each port in the specified array has a pending item. It then returns the
result as a array.
let recv (p : Port<string> array) =
async {
let! results = Receive.from_multiple p
printfn "%i results received." results.Length
}
*)
[<OverloadID("from_multiple")>]
static member from_multiple (p : Port<'a> array) =
Async.Primitive(fun (cont, econt) ->
Arbiter.MultiplePortReceive(false, p, fun r -> cont r)
|> Receive.activate)
The Overloads are defined because each of these members has an alternate version that takes a timeout limit. I’ll cover those in the next post.
29 comments:
-
最近流行の家出掲示板では、各地のネットカフェ等を泊り歩いている家出少女のメッセージが多数書き込みされています。彼女たちはお金がないので掲示板で知り合った男性の家にでもすぐに泊まりに行くようです。あなたも書き込みに返事を返してみませんか
-
性欲を持て余し、欲求不満になっている女性を金銭の対価を得て、癒して差し上げるお仕事です。参加にあたり用紙、学歴等は一切問いません。高収入アルバイトに興味のある方はぜひどうぞ
-
童貞を奪ってみたい女性たちは、男性にとって「初体験」という一生に一度だけの、特別なイベントを共に心に刻み込むことを至上の喜びにしているのです。そんな童貞好きな女性たちと高級チェリーで最高のSEXをしてみませんか
-
最近寂しくて困っています。夜一人で寝るのが凄く寂しいです…隣で添い寝してくれる男性いませんか?見た目とか特に気にしません。優しくて一緒にいてくれる方大歓迎☆一緒に布団で温まりましょう♪shart.enamorado.de-me@docomo.ne.jp
-
一晩の割り切ったお付き合いで副収入が得られるサイトのご案内です。アルバイト感覚での挑戦もできる、安心の無料登録システムを採用しておりますので、興味のある方は当サイトをぜひご覧ください
-
復活、スタービーチ!日本最大の友達探しサイトがついに復活、進化を遂げた新生スタビをやってみませんか?理想のパートナー探しの手助け、合コンパーティー等も随時開催しています。楽しかった頃のスタビを体験しよう
-
なかなか彼氏、彼女が出来ない君達の深層心理を徹底解明♪みんなでモテる度チェックをやって結果交換も自由、合コンや休み時間はモテる度チェックで暇つぶし!次にモテ期が訪れる瞬間をズバリ診断しちゃいます
-
出会ぃも今は¥倶楽部!オンナがオトコを買う時代になりました。当サイトでは逆援希望の女性が男性を自由に選べるシステムを採用しています。経済的に成功を収めた女性ほど金銭面は豊かですが愛に飢えているのです。いますぐTOPページからどうぞ
-
今迄は野外露出がマイナスイメージと囚われがちですが、実際は開放的な気分になり有名人のヌーディストが、オープンになる事を推奨してるぐらいです。このサイトをキッカケに知り合った娘達と野外で楽しみませんか
-
どうしても相手がセレブだと高級感が有り、近付きにくいと思われがちですが、実際はただ欲望のままに快楽を追い求める、セレブとは掛け離れた女性が居るだけです。今こそ自分の欲望を満たすときです
-
最近旦那とマンネリで全然Hしてません。正直もうかなり欲求不満です…誰か相手してくれる方いませんか?空いている時間は多いと思うので都合は合わせやすいと思います。お互い楽しめる関係になりたいな。人妻でも平気な人いたら是非相手してください☆一応18歳以上の人限定でお願いします。上はどこまででも大丈夫なんで excellent.lady@docomo.ne.jp
-
当サイトでは無料でオナ動画を見ることができます。また、ライブチャット機能でリアルタイムオ○ニーを見るチャンスも高く、興奮間違いなしです。また、一人Hのお手伝いを希望される女性もあり、お手伝いいただけた方には謝礼をお支払いしております
-
日本最大、だれもが知っている出会い系スタービーチがついに復活、進化を遂げた新生スタビをやってみませんか?趣味の合う理想のパートナー探しの手助け、合コンパーティー等も随時開催しています。楽しかった頃のスタビで遊んでみよう
-
あなたの異性からのモテ度数を診断できる、モテる度チェッカー!日頃モテモテで充実しているあなたもそうでないニートの方も隠されたモテスキルを測定して結果を活用し、今以上にモッテモテになること間違いなし
-
女性のオナニーを助ける場が救援部です。ここに所属してる娘のオナニーを見て気に入ったら、実際に会ってオナニーを手伝っても良いし、エッチしても良し、これで報酬Get出来るんですから美味しいバイトですよ
-
一時代を築いたスタービーチは閉鎖になりましたが、もう一度楽しい思いをしたい、もう一度出会いたいと思う有志により再度復活しました。本家以上に簡単に出会えて楽しい思いを約束します
-
誰にも言えない秘密があります。実はとってもHなんです、せっかく女として生まれたからにはアブノーマルな世界に飛び込んでみたいです☆普段では考えられないプレイを思う存分楽しみ、経験したいんです♪快楽に溺れさせてくれませんか?一緒に感じ合いましょう!!都合はつくのですぐに時間を合わせられます。18歳よりも上の方がいいです!! quietness@docomo.ne.jp
-
流出サイトでは、有名人から素人までの他では見れない秘蔵の動画を入手しています。何より素人が相手の場合に限り、アポを採る事も可能です。動画でお手軽に抜いて、抜き足らない場合は、女の子にハメて来て下さい
-
日本最大級、だれもが知っている出会い系スタービーチがついに復活、グリーより面白い新生スタビをやってみませんか?趣味の合う理想のパートナー探し、合コンパーティーに興味がある方はぜひ無料登録してみてください。楽しかった頃のスタビで遊んでみよう
-
女性には風俗がない!そんな悩みを持つセレブ女たちは、リッチセックスでお金を使い自分を満たします。金銭面では豊かですが、愛に飢えている彼女たちを癒して高額な報酬を手に入れてみませんか
-
女子○生の個人情報公開!?遊び盛りの神待ち女子○生の写メ・アドレス・番号を公開中!好みの女の子を選んで直メ・直電で今すぐ待ち合わせしよう
-
高級チェリーの冬は童貞卒業のシーズンです。童貞を食べたい女性達もウズウズしながら貴方との出会いを待っています。そんな女性達に童貞を捧げ、貴方もハッピーライフを送ってみませんか
-
初書き込みで申し訳ないんですが、都合のいい男性探しています。不況の中でも会社が高成長してて、忙しい毎日です。お陰でプライベートが充実していなくって、溜まる一方です。財産的にも多少余裕が今のところあるのでお礼もできます。何より、この書き込みが読まれているのかちょっと怪しいですけど…。アドレス置いとくので、消されないうちにメールくれたら嬉しいです。inspiration.you@docomo.ne.jp
-
結婚してから女としての喜びを失った玉の輿女性達、エリート旦那のそつのない動きには満足できるはずもなく、時間を持て余すお昼時に旦那のお金を使い、出張ホストサービスを楽しむそうでございます。今回も10万円での愛を承っております。癒しの一時をご一緒して謝礼を貰ってくださいませ
-
だれもが知っている日本で一番有名な出会い系スタービーチがついに復活、greeより面白い新生スタビをやってみませんか?理想のパートナー探し、合コンパーティーに興味がある方はぜひ無料登録してみてください
-
当サイトは、みんなが玉の輿に乗れるかどうか診断できる性格診断のサイトです。ホントのあなたをズバリ分析しちゃいます!玉の輿度チェッカーの診断結果には、期待以上の意外な結果があるかも
-
男性との甘い一時が奥様達には必要になっております。刺激のない私生活はとても辛く、ココロもカラダもストレスが堪る一方、そんな中にデリバリーホストに癒しを求めている奥様、セレブ女性は大変増えてきており、男性の方が不足状態です。女性達の癒しとなる仕事をあなた様も一度体験してみてはいかがでしょうか
-
メル友らんどでは誰でも気軽にメル友が作れちゃう、参加無料でいつでも利用可能なコミュニティサイト♪ご近所の気の合うリア友や、真面目に彼氏彼女探しなど、楽しみ方は無限大!自分にぴったりの相手を見つけちゃおう
-
大好評の逆ナンイベントが毎週開催決定!素敵な出会いのきっかけ探し・アイナビにきませんか?積極的な出会いを求める人達なら無料参加OK!あなたもほんの少しの勇気で素敵な彼氏・彼女をGETしちゃおう