Error during initialization

question

#1

I hate to ask these kind of questions, but I can’t understand why this code doesn’t work. Apparently the problem is a stackoverflow error, which seems to be generated in the build_bar() function, when assigning. The new BarType is initially a vector of undef values, then I initialize it.
As far as I know, this should be legal, since I also tested a more complex code (with parametric types) which does likewise but works fine.
Any tip? Thanks!

using OffsetArrays

struct FooType <: AbstractArray{Float64,1}
data::OffsetArray{Float64,1}
dim::Int64
end

FooType(n::Int) = FooType(OffsetArray(Float64, 1:n), n)
Base.size(s::FooType) = (s.dim,)
Base.IndexStyle(::Type{<:FooType}) = IndexLinear()
Base.similar(s::FooType, ::Type, d::Dims) = FooType(d[1])
Base.getindex(s::FooType, i::Int) = s.data[i]
Base.setindex!(s::FooType, v, i::Int) = (s.data[i] = v)
Base.show(io::IO, s::FooType) = print(io, s)
Base.indices(s::FooType) = indices(s.data)
Base.:(==)(a::FooType, b::FooType) = a.data == b.data
Base.isless(a::FooType, b::FooType) = a[1]<b[1]

struct BarType <: AbstractArray{FooType,1}
data::Array{FooType,1}
dim::Int64
end

function build_bar(m::Int, n::Int)
bar = BarType(Array{FooType,1}(m), m)
for i in 1:m
bar.data[i] = FooType(n)
end
bar
end

BarType(m::Int, n::Int) = build_bar(m,n)
Base.size(b::BarType) = (b.dim,)
Base.IndexStyle(::Type{<:BarType}) = IndexLinear()
Base.similar(b::BarType, ::Type, d::Dims) = BarType(d[1])
Base.getindex(b::BarType, i::Int) = b.data[i]
Base.setindex!(b::BarType, val, i::Int) = (b.data[i] = val)
Base.show(io::IO, b::BarType) = print(io, b.dim)
Base.indices(b::BarType) = indices(b.data)

b = BarType(3,2)


#2

Your show method calls print which calls show which calls print which calls show etc, which is how you get a stack overflow error. This only happens at the end of your code when Julia tries to display your BarType and its contained FooTypes. The easiest thing to do is to just delete that show method since it’s doing nothing useful for you.

If you want a custom show() make sure that what you print() isn’t just the same thing that was passed to show(). For example, this works fine:

julia> Base.show(io::IO, s::FooType) = print(io, "FooType with data: $(s.data)")

julia> b = BarType(3,2)
3-element BarType:
 FooType with data: [NaN, 0.0]
 FooType with data: [2.42531e-314, 2.29997e-314]
 FooType with data: [2.97131e-320, 0.0]