CartesianIndices and oneunit()


#1

I’m trying to run the following code from Tim Holy’s blog post to learn about Cartesian indices:

function boxcar3(A::AbstractArray)
    out = similar(A)
    R = CartesianIndices(A)
    Ifirst, Ilast = first(R), last(R)
    I1 = oneunit(Ifirst) # <------------------------------------
    for I in R
        n, s = 0, zero(eltype(out))
        for J in max(Ifirst, I - I1):min(Ilast, I + I1)
            s += A[J]
            n += 1
        end
        out[I] = s/n
    end
    return out
end

a = zeros(Int, 10, 10); a[5, 5] = 1

boxcar3(a)

but I get the following error:

ERROR: LoadError: MethodError: no method matching CartesianIndex{2}(::CartesianIndex{2})
Closest candidates are:
  CartesianIndex{2}() where N at multidimensional.jl:73
  CartesianIndex{2}(::Integer...) where N at multidimensional.jl:69
  CartesianIndex{2}(::Tuple{Vararg{Integer,N}}) where N at multidimensional.jl:64
  ...
Stacktrace:
 [1] oneunit(::CartesianIndex{2}) at ./number.jl:320

#2

I think you need 1.1 to make it work (it works for me with 1.1-rc1 but not on 1.0.2)


#3

Ah, thanks! Some time travelling is going on, I see. :slight_smile: I wonder if there’s a more compatible version that works for all Julia 1. versions…


#4

1.1 got that functionality in order to prettify the code in the blog post. Writing documentation is often one of the best ways of figuring out what’s wrong with your API. Since I don’t relish rewriting the blog post multiple times, I just focused on the long term.

EDIT: if you want to do this on 1.0, with a little bit of piracy you can locally add the code in these PRs:


#5

Wait, I thought Julia 1.0+ was stable and without breaking changes? I don’t really know what defines breaking change but if a code works on 1.1 but not on 1.0, isn’t that breaking?


#6

Backward compatibility = non-breaking changes: code developed using an earlier version of Julia will continue to work when executed using a later version of Julia.

Forward compatibility: code developed using a later version of Julia will also work when executed using an earlier version of Julia.

Backward compatible code does not have to be forward compatible.


#7

It still gives me errors (latest Julia 1.2.0-DEV.165, Windows 10, also Julia 1.1.0-rc1.0)

julia> boxcar3(a)
ERROR: InexactError: Int64(0.1111111111111111)
Stacktrace:
 [1] Type at .\float.jl:703 [inlined]
 [2] convert at .\number.jl:7 [inlined]
 [3] setindex! at .\array.jl:769 [inlined]
 [4] setindex! at .\multidimensional.jl:460 [inlined]
 [5] boxcar3(::Array{Int64,2}) at .\REPL[1]:12
 [6] top-level scope at REPL[3]:1

#8

In the blog post, check the first bullet point after the phrase “Let’s walk through this line by line” and compare that to the error message you’re getting.


#9

Thank you, I see.