I asked a question about this earlier but I don't think I really knew what I was asking. I think I understand my problem slightly better now.
I'm using netwire, an arrowized FRP library, and having some trouble getting this arrowloop implemented.
I have
f :: ArrowLoop r => a -> r [a] a
g :: ArrowLoop r => [a] -> r () [a]
Such that g
basically ties every element in the given list with the list of every other element using f
...um...this is hard to really say using words so I'll give an example with a list of length 4:
g [x0, x1, x2, x3] = proc _ -> do
rec
y0 <- f x0 -< [y1, y2, y3]
y1 <- f x1 -< [y0, y2, y3]
y2 <- f x2 -< [y0, y1, y3]
y3 <- f x3 -< [y0, y1, y2]
returnA -< [y0, y1, y2, y3]
(I have a helper function selects :: [a] -> [(a,[a])]
, that turns something like [x,y,z]
into [(x, [y,z]), (y, [x,z]), (x, [x,y])]
)
Now...I've compiled this hard-coded version and this already works and delivers exactly the results that I wanted mostly. It runs without any funky <> issues.
Does anyone know if it's possible to do this "exact" thing...but with a general number of list elements?
For reference, my implementation of selects
comes from Simon Marlow,
selects :: [a] -> [(a,[a])]
selects = go []
where
go xs [] = []
go xs (y:ys) = (y,xs++ys) : go (y:xs) ys
I couldn't test this properly since I didn't have any example
f
to run it against but I believe this generalizes the arrow pattern you have:So first we map with
f
to get the list of arrows[f x0, f x1, ...]
and then we feed it to a combinator I namedlistLoop
which takes a list of arrows and defines a recursive arrow which essentially has the same logic as yourselects
.bs
is the list of results from arrows precedingr
(analogous toxs
inselects
) andas
are the results from the arrows followingr
. For eachr
we feed in the results of the other arrows but not the result ofr
itself (which isa
). Then we recurse, appendinga
to the list of preceding results.