В чем разница между коммутацией и изменением в Clojure?

Я пытаюсь написать очень простой код, который показывает разные результаты между коммутацией и изменением в Clojure. Может ли кто-нибудь создать пример для этой цели?

Чем проще, тем лучше понять разницу.


person lambda-pumpkin    schedule 25.05.2016    source источник
comment
Я не думаю, что это не по теме. Он требует примера, но с таким же успехом его можно было бы сформулировать так: «В чем разница между коммутацией и пересадкой?» Может ли кто-нибудь показать мне функцию, которая демонстрирует, что они ведут себя по-разному?   -  person amalloy    schedule 25.05.2016
comment
Я согласен, что это правильный и явно не дублирующий вопрос. На ум не приходит простого ответа, потому что они оба всегда дают один и тот же ответ, просто иногда делают это в разное время.   -  person Arthur Ulfeldt    schedule 25.05.2016


Ответы (1)


Предполагая, что commute используется правильно, не должно быть никакой разницы в наблюдаемых значениях Refs, за исключением того, что использование commute может помочь фиксации транзакции в сценарии с высокой конкуренцией, где это было бы трудно сделать с alter. Конечно, когда это применимо, это довольно значительная разница в результате…

Легче проиллюстрировать, чем именно отличаются вещи, используя побочные эффекты. Вот однопоточный пример, иллюстрирующий основное свойство, которое

  • alter будет вызываться ровно один раз за "попытку транзакции" (возможно, только один раз),

  • commute будет вызываться ровно один раз за "попытку транзакции" (в то время как commute не вызовет их, он может быть задействован в повторных попытках, если alter используется в том же блоке dosync), а затем в последний раз для вычисления зафиксированного значения (поэтому как минимум дважды , хотя опять же, это не вызовет повторных попыток само по себе):


user=> (def r (ref nil))
#'user/r
user=> (dosync (alter r prn))
nil
nil
user=> (dosync (commute r prn))
nil
nil
nil

Используя несколько Thread/sleeps и несколько потоков, можно спровоцировать больше повторных попыток на стороне alter, при этом наблюдая две повторные попытки на стороне commute, исследовать влияние на историю ссылок использования одного или другого и т. д.

person Michał Marczyk    schedule 25.05.2016