Internal representation of `using Foo`


#1

When trying to make Lint.jl working in Juno with Julia 1.0.1, I realised that Lint would stumble across any line with using [...].
Digging into the root cause I found that dump(:(using Foo)) has different results in different Julia versions:

julia-0.6.2.2> dump(:(using Foo))
Expr
  head: Symbol using
  args: Array{Any}((1,))
    1: Symbol Foo
  typ: Any
julia-1.0.1> dump(:(using Foo))
Expr
  head: Symbol using
  args: Array{Any}((1,))
    1: Expr
      head: Symbol .
      args: Array{Any}((1,))
        1: Symbol Foo

Is this by purpose? It seems a bit odd, as

julia-1.0.1> Expr(:using,:Foo)
:(using Foo)

but

julia-1.0.1> dump(Expr(:using,:Foo))
Expr
  head: Symbol using
  args: Array{Any}((1,))
    1: Symbol Foo

Maybe, I have missed something?


#2

The AST representation of various things was not stable prior to 1.0.


#3

My concern is not so much the stability of AST between Julia versions, it is more that the output of dump(Expr(:using,:Foo)) is not identical to dump(:(using Foo)) although Expr(:using,:Foo) evaluates to :(using Foo).
Funny enough, dump(Expr(:using,:Foo)) == dump(:(using Foo)) evaluates to true


#4

The expression type for using is undocumented, you should consider opening an issue.


#5

Yes, this representation is intentional. The idea is that the Expr with head . is a “path expression”, a dot-delimited list of names giving the components of a module path. In general:

julia> dump(:(using A.B.C.D))
Expr
  head: Symbol using
  args: Array{Any}((1,))
    1: Expr
      head: Symbol .
      args: Array{Any}((4,))
        1: Symbol A
        2: Symbol B
        3: Symbol C
        4: Symbol D

So for using A the dot expression has a single argument.

Indeed there are a couple rough edges to fix here:

  • The printing for Expr(:using, :Foo) should use that input form instead of using Foo, since as you note they don’t match.
  • This should be added to the AST devdocs.
  • There should be an error for evaluating Expr(:using, :Foo), or perhaps we should treat it the same as using Foo.

That would be because dump always returns nothing! :slight_smile: