I’m fresh new to Elixir. I’m trying to port a golang library to elixir. But I don’t know how to deal with the the loop part. As a functional programming language. Elixir provides no loop.
func (r *ISAAC) isaac() {
r.cc = r.cc + 1 /* cc just gets incremented once per 256 results */
r.bb = r.bb + r.cc /* then combined with bb */
for i := 0; i < 256; i++ {
x := r.mm[i]
switch i % 4 {
case 0:
r.aa = r.aa ^ (r.aa << 13)
case 1:
r.aa = r.aa ^ (r.aa >> 6)
case 2:
r.aa = r.aa ^ (r.aa << 2)
case 3:
r.aa = r.aa ^ (r.aa >> 16)
}
r.aa = r.mm[(i+128)%256] + r.aa
y := r.mm[(x>>2)%256] + r.aa + r.bb
r.mm[i] = y
r.bb = r.mm[(y>>10)%256] + x
r.randrsl[i] = r.bb
}
/* Note that bits 2..9 are chosen from x but 10..17 are chosen
from y. The only important thing here is that 2..9 and 10..17
don't overlap. 2..9 and 10..17 were then chosen for speed in
the optimized version (rand.c) */
/* See http://burtleburtle.net/bob/rand/isaac.html
for further explanations and analysis. */
}
Its hard to say without knowing what ISAAC looks like internally…
But loops are generally replaced by recursion or higher order functions in Enum.
In general I tend to avoid mechanical translations and rewrite from scratch.
There are a lot of concepts in go that you can’t use in elixir. Some do not have even a direct equivalen, like the massive amount of mutation you do in your code.
If its crypto, don’t touch it. First rule of crypto is to not do it yourself but to use libraries that have been there for a while and are battleproven.
Just implement some bindings to the C or GO versions via NIFs or C-Ports, or use some package from hex.pm if available, or take a look at the erlang :crypto module.
Pointing to recursion, comprehensions, and higher-order functions only help so much. They tell us what the desired result will look like, or should look like, but not how to get there
@AlecHsueh Once you know what you’re doing, whether that’s by reading that particular Go fragment or not, then you can give it a go in Elixir. It’s hard to get rid of the for and the mutation with a line-by-line translation but understanding it helps to get to something that’s more Elixir-like.
There’s a collection of some kind underlying most fragments that have a C-like for. A brief glance at the above suggests that it involves byte manipulation or binary data. An Elixir Binary, along with a binary comprehension, and a bunch of meaningful functions might be an idiomatic choice here