Недавно я начал читать о языке программирования Go, и мне показалось, что переменные канала очень привлекательны. Можно ли подражать той же концепции в Haskell? Может быть, иметь тип данных Channel a
и структуру монад, чтобы включить изменяемое состояние и функции, которые работают как ключевое слово go
.
Я не очень хорошо разбираюсь в параллельном программировании, и простой механизм передачи каналов, подобный этому в Haskell, действительно облегчил бы мне жизнь.
ИЗМЕНИТЬ
Люди просили меня уточнить, какие шаблоны Go мне интересно перевести на Haskell. Итак, в Go есть канальные переменные первого класса, которые могут передаваться и возвращаться функциями. Я могу читать и писать в эти каналы, и поэтому легко обмениваюсь данными между подпрограммами, которые могут выполняться одновременно. Go также имеет ключевое слово go
, которое в соответствии со спецификацией языка инициирует выполнение функции одновременно как независимый поток и продолжает выполнение кода без ожидания.
Точный шаблон, который меня интересует, выглядит примерно так (синтаксис Go странный - переменные объявляются с помощью varName varType вместо обычного перевернутого способа - но я думаю, что он читаем):
func generateStep(ch chan int) {
//ch is a variable of type chan int, which is a channel that comunicate integers
for {
ch <- randomInteger() //just sends random integers in the channel
}
func filter(input, output chan int) {
state int
for {
step <- input //reads an int from the input channel
newstate := update(state, step) //update the variable with some update function
if criteria(newstate, state) {
state = newstate // if the newstate pass some criteria, accept the update
}
output <- state //pass it to the output channel
}
}
func main() {
intChan := make(chan int)
mcChan := make(chan int)
go generateStep(intChan) // execute the channels concurrently
go filter(intChan, mcChan)
for i:=0; i<numSteps; i++ {
x <- mcChan // get values from the filtered channel
accumulateStats(x) // calculate some statistics
}
printStatisticsAbout(x)
}
Мой основной интерес - моделирование методом Монте-Карло, в котором я генерирую конфигурации последовательно, пытаясь изменить текущее состояние системы и принимая модификацию, если она удовлетворяет некоторым критериям.
Тот факт, что с помощью этих каналов я мог написать очень простую, удобочитаемую и небольшую симуляцию Монте-Карло, которая будет выполняться параллельно в моем многоядерном процессоре, действительно впечатлил меня.
Проблема в том, что у Go есть некоторые ограничения (особенно, в нем отсутствует полиморфизм, как я привык в Haskell), и, кроме того, мне очень нравится Haskell, и я не хочу отказываться от него. Итак, вопрос в том, есть ли способ использовать какую-то механику, похожую на приведенный выше код, чтобы легко выполнять параллельное моделирование в Haskell.
EDIT (2, context): Я не изучал компьютерные науки, особенно параллелизм. Я просто парень, который создает простые программы для решения простых задач в моей повседневной исследовательской работе в дисциплине, совершенно не связанной с CS. Мне просто интересно то, как работает Haskell, и я люблю использовать его для выполнения своих небольших задач.
Я никогда не слышал только о пи-исчислении или каналах CSP. Извините, если вопрос кажется некорректным, возможно, это моя вина из-за огромного незнания этого вопроса.
Вы правы, я должен быть более конкретным в отношении того, какой шаблон в Go я хотел бы воспроизвести в Haskell, и я постараюсь отредактировать вопрос, чтобы он был более конкретным. Но не ждите глубоких теоретических вопросов. Дело в том, что из немногих вещей, которые я прочитал и закодировал, кажется, что у Go есть изящный способ реализовать параллелизм (и в моем случае это просто означает, что моя работа по заставлению всех моих ядер гудеть числовыми вычислениями проще), и если бы я мог использовать аналогичный синтаксис в Haskell, я был бы рад.