簡體   English   中英

與Clojure中的STM並發

[英]Concurrency with STM in Clojure

我目前正在學習Clojure,並且不確定如何使用STM進行並發。 我要完成的任務非常簡單,我有一個字符串向量,我想同時在每個字符串上運行一個函數,並用函數返回的值替換該字符串。

我目前可以使用pmap輕松完成此操作:

(pmap function string_vector)

如何在Clojure中使用STM做同樣的事情?

STM是一種跨線程共享數據的方式。 如果您根本不需要協調(在此示例中不需要協調),則沒有使用STM的真正理由。

Clojure中的STM是關於隨着時間的推移保持易變事物的狀態。 這些狀態會隨時變化的事物被稱為具有“身份”。 就像您一生都擁有“您”的身份一樣,即使三個月大的“您”可能無法識別120歲的“您”。 因此,讓我們在您的示例中添加一些可變的內容,以便我們有理由使用STM:

讓我們在公共可變的地方存儲字符串,然后在其中並行更改它們:

user> (def current-strings (ref ["a" "b" "c"]))
#'user/current-strings
user> (dosync (alter current-strings (fn [the-string-at-this-instant]
                                       (pmap #(.toUpperCase %) the-string-at-this-instant))))
("A" "B" "C")
user> @current-strings
("A" "B" "C")
user> 

在此示例中,我們創建了一個事務,該事務通過向其應用函數來更改字符串集合的狀態。 在內部,該函數恰好並行計算新值。

為了使這一點更有趣,讓我們創建一個可變事物的向量,然后並行更新一堆獨立可變的事物,每個事物在它自己的事務中:

user> (def current-strings [(ref "a") (ref "b") (ref "c")])
#'user/current-strings

user> (doall
       (pmap (fn [ref-to-update]
               (dosync (alter ref-to-update #(.toUpperCase %))))
             current-strings))
("A" "B" "C")

user> (map deref current-strings)
("A" "B" "C")
user> 

如您所見,所有這些都不需要STM,因為所有這些操作都可以使用clojure中的其他可變類型來處理,所以原子將是一個不錯的選擇。 和裁判一起玩也很有趣! 玩得開心!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM