-
-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
More transducers #49735
Comments
Are you suggesting that IR itself should better represent transducers, or simply that transducers generates better IR as is? |
Both actually. At least in theory, if we moved from representing loops with In practice, I wouldn't be at all surprised though if it was simply WAY too big a task to change how we internally represent loops, especially given that we've already developed the infrastructure for rediscovering loop flow information inside the compiler with our current goto-based representation. I just mentioned that as a very far off possible milestone. |
The main thing that would potentially improve with a foldl based loop IR is that it might allow us to prove that most loops terminate which would make concrete eval a lot more powerful. |
Especially for statically sized objects like Tuples |
But what if you don't want to do |
|
Maybe put another way @stevengj, what's nice about working with this different style is that all the logic and operations of the loop are encoded in the transducer and the reducing operator, and then the details of how it's scheduled and run (i.e. sequential or pairwise, or parallel or whatever) can be changed by simply swapping This lets you re-use more code. i.e. in the example I showed above: foldxl(+, xs |> Map(x -> 2x) |> Filter(iseven)) the reducing operator is Because iterators are inherent sequential, turning the iterator equivalent of this operation into a parallel or pairwise reduction is pretty non-trivial. |
I guess I got confused by this description:
Because what you are describing is not |
Maybe it could say:
|
This has been mentioned in a few scattered places (e.g. here #15648 (comment), #33526, various slack and discourse threads, etc.), but I think it'd be good to have a general tracking issue for this as a large scale goal.
Currently, the majority of our infrastructure is built on the paradigm of iterators. These are essentially state machines that tell you how to progress from one state to the next.
Something @tkf was rightfully a big champion of was the use of transducers instead of iterators where possible, with https://github.com/JuliaFolds/Transducers.jl being his gigantic playground for those ideas.
Fundamentally, the idea with transducers is that you replace
iterate
as your fundamental operation for traversing data, withfoldl
, and this enables a lot of interesting things. To borrow from the docs in Transducers.jl, this is whatis essentially doing:
the Transducers.jl equivalent
does this:
and this is obtained not though clever compiler magic, but just algorithm design. The difference is that with iterators, one writes a loop and pulls values out of the iterator. The loop owns the iterator. With transducers, the transducer owns the loop and pushes out values.
An important practical benefit of transducers is the space of parallelism. Transducers.jl and things built on it like https://github.com/tkf/ThreadsX.jl give really nice APIs for many parallel workflows because whether an algorithm is amenable to parallelism is built into the representation of a transducer. With iterators, many of these things are quite opaque since the fundamental paradigm of iteration is sequential.
Finally, I'll also mention that because our intermediate representations (IR) represent loops in terms of
while
loops (goto
s) on iterators, this makes it a real pain to take lowered julia code and find out what the structure and intent of the original code was, and a lot of IR level transformations on Julia code need to do a lot of work to rediscover what the original loop layout was.When represented in terms of
fold
s though, we could preserve a lot more structured information at the IR level which could make compiler level loop optimizations easier.The text was updated successfully, but these errors were encountered: