Approach to iterative functions in julia?

Hello, I’ve just spent yesterday learning Julia and it’s been a blast! Previously, I used Python and Lua for quick projects. In those languages, I used iterative functions (or generators) but I’m having a hard time figuring out how to translate that idea to Julia.

Here’s an exercise I’m doing:

function find_all_contiguous(contrafinder::Function, a::Union{AbstractArray,AbstractString})
    firsti, lasti = firstindex(a), lastindex(a)
    i = firsti
    while i <= lasti
        cstop = contrafinder(a, i, lasti)
        if isa(cstop, Integer)
            # i want to yield here instead of returning on first match
            return i, clamp(cstop, firsti, lasti)
            i = cstop
        end
        i += 1
    end
end

function as_contrafinder(pred::Function)
    # a way to more succintly express this would also be nice to have
    return function (a::AbstractVector{<:Any}, start::Integer, stop::Integer)
        for i in start:stop
            if !pred(a[i])
                if i == start
                    return
                else
                    return i-1
                end
            end
        end
    end
end

# example use
# intent: from a randomly populated array, print the sequences of
# odds found and the sum of that sequence
data = rand(0:9, 1000)
for (start, stop) in find_all_contiguous(isodd |> as_contrafinder, data)
    seq = data[start:stop]
    println("sum of odd sequence $(seq) = $(sum(seq))")
end

Thank you in advance! :heart:

There are a number of packages that aim to provide generator functionality,

is one such package. See also this thread for additional modeling patterns, including making use of Channel and the julia native generator

1 Like

Thanks for the response! Implementing iterators natively in Julia seems very messy, so the package recommendation is much appreciated

It’s really just to replace yield with put!:

squares = Channel{Int}() do ch
    for i in 1:10
        put!(ch, i^2)
    end
end

println(sum(squares))

And the standard iterators in julia are similar to python’s, except you define Base.iterate instead of __iter__ and __next__.

See Interfaces · The Julia Language and Asynchronous Programming · The Julia Language

2 Likes