Correct use of convert

The last line in the program below fails with the error

ERROR: LoadError: MethodError: Cannot convert an object of type String to an object of type Symbol

The message is misleading, because it certainly can do such a conversion as the line before it demonstrates. More importantly, how do I write the convert statement in such a way that the last statement works? Thanks!

convert(::Type{Symbol}, x::String) = Symbol(x)
b = Vector{Symbol}(undef,2)
println( convert( Symbol,  "hi"  ) )
b[:] = [ "hi"; "hello" ]

Does using Base.convert work?

2 Likes

No. That already fails on line 3.

I meant the method definition

1 Like

ha, it does! Thanks!! I understand what’s happening. Gee. That’s easy.

Also note that you should not define this method for Base.convert. It’s type piracy and can break code for everyone else.

2 Likes

Thanks @yuyichao .

Ok, how could I address this issue without committing type piracy?

By making sure to turn the data you’re writing into b into Symbols first. E.g.

b .= Symbol.(["hi", "hello"])

Thanks and sure.

But that’s not the question I meant to ask. What I meant to ask was: How can I get this conversion to work automatically?

You should no do that.

1 Like

Make your own type so it’s not piracy :man_shrugging:

struct MyVector{T} <: AbstractVector{T}
    v::Vector{T}
end

# (among many other methods...)
Base.setindex!(v::MyVector{T}, x, i) = v.v[i] = T(x)
julia> MV = MyVector(Symbol[:a, :b, :c]);

julia> MV.v
3-element Array{Symbol,1}:
 :a
 :b
 :c

julia> MV[2] = "q"
"q"

julia> MV.v
3-element Array{Symbol,1}:
 :a
 :q
 :c

I would look for the most obvious way to make do without the automatic conversion, as @yuyichao suggests…

2 Likes

There’s a school of thought that type conversions should not occur automatically/implicitly, and some languages do not support implicit conversions. Clearly the designer’s of Julia do not adhere to that, but gratuitous implicit conversions can lead to confusing, abstruse or erroneous code. See javascript, for example.

1 Like