# \`iterate\` returning iter, next-state and iter's original length

**URL:** https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656
**Category:** General Usage
**Created:** [September 7, 2018, 8:49am UTC](https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656 "2018-09-07T08:49:07Z")
**Posts on this page:** 5
**Page:** 1

<div class="post-metadata">

### Author: ![JeffreySarnoff](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jeffreysarnoff/32/1980_2.png) [@JeffreySarnoff](https://discourse.julialang.org/u/JeffreySarnoff)
#### Post date: [September 7, 2018, 8:49am UTC](https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656/1 "2018-09-07T08:49:07Z")

</div>

I am using a custom iterator that delegates into a struct to obtain the iterative grist, say a vector. I think it is appropriate to check if the current state (like an index) exceeds the length of the delegatee.

I do not want to recalculate the vector’s length at each iteration, and keeping the length in the struct does not work for external reasons.

What is an appropriate way to define `iterate` so that the next state returned is a tuple `(total_length, next_index)` and have it all work? I would prefer that the state stay simple (a two tuple) rather than embed both in a struct.

---

<div class="post-metadata">

### Author: ![Tamas\_Papp](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/tamas_papp/32/25949_2.png) [@Tamas\_Papp](https://discourse.julialang.org/u/Tamas_Papp)
#### Post date: [September 7, 2018, 9:14am UTC](https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656/2 "2018-09-07T09:14:35Z")

</div>

```julia
struct Foo{T <: AbstractVector} # type for MWE
    v::T
end

function Base.length(c::Foo)
    @info "length was called, and it was darn expensive"
    length(c.v)
end

function Base.iterate(c::Foo)
    len = length(c)
    len > 0 || return nothing
    (c.v[1], (2, len))
end

Base.iterate(c::Foo, (i, len)) = i > len ? nothing : (c.v[i], (i+1, len))

```

then

```julia
julia> foreach(println, Foo(1:10))
[ Info: length was called, and it was darn expensive
1
2
3
4
5
6
7
8
9
10

```

But that said, I would just define a wrapper type that caches the length.

---

<div class="post-metadata">

### Author: ![dpsanders](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/dpsanders/32/3573_2.png) [@dpsanders](https://discourse.julialang.org/u/dpsanders)
#### Post date: [September 7, 2018, 9:30am UTC](https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656/3 "2018-09-07T09:30:54Z")

</div>

Doesn’t a vector know its length?

---

<div class="post-metadata">

### Author: ![JeffreySarnoff](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jeffreysarnoff/32/1980_2.png) [@JeffreySarnoff](https://discourse.julialang.org/u/JeffreySarnoff)
#### Post date: [September 7, 2018, 9:32am UTC](https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656/4 "2018-09-07T09:32:23Z")

</div>

strings do not know their length  
although I am not using strings here

You may have resolved this as Julia does, often – problem? no, its no problem.

The length I need is several layers deep into substructure while iterating on `x` length(`x.partsofx.vecparts.bluevec`). I don’t believe the levels of dot indirection are very costly – I do believe they are not ameanable to compile time prelocation.

---

<div class="post-metadata">

### Author: ![JeffreySarnoff](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jeffreysarnoff/32/1980_2.png) [@JeffreySarnoff](https://discourse.julialang.org/u/JeffreySarnoff)
#### Post date: [September 7, 2018, 9:37am UTC](https://discourse.julialang.org/t/iterate-returning-iter-next-state-and-iters-original-length/14656/5 "2018-09-07T09:37:47Z")

</div>

thanks for that … I was looking for `(c, (i, len))`

I’ll benchmark both approaches.
