-
-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
What is the semantics of importing a top-level module from a sub-module? #38011
Comments
It brings all exported symbols in but you haven't defined |
@KristofferC Sorry, I did not formulate my question well. It is perfectly expected that the code will result in an error if you uncomment the line My question was about the semantics of module TestPackage
export x, y
x = 0
module Sub
using TestPackage # or alternatively `using ..TestPackage`
z = x
end
y = 1
end My hypothesis is that it brings all exported symbols that are defined in TestPackage before Sub into scope. But I did not see this documented anywhere and I am unsure whether or not I can rely on it. |
How did this hypothesis form? Some minimal testing doesn't seem to agree with that: julia> module TestPackage
export x, y
x = 0
module Sub
using ..TestPackage # or alternatively `using ..TestPackage`
f() = y
end
y = 1
end
Main.TestPackage
julia> TestPackage.Sub.f()
1 |
Interesting. I did not test this exact scenario. module TestPackage
export x, y
x = 0
module Sub
using ..TestPackage
z = y # error!
end
y = 1
end But all of this makes my question all the more relevant. |
You are trying to use |
Based on your example and on my knowledge of Julia's internals, I think I understand what But I think you would be wrong to think that this behavior is self-evident and not worth documenting better. I know languages in which such a "recursive" import would be forbidden, and Julia could have plausibly been one of them. Also, I know languages where it is allowed but where the snippet you shared would be rejected (as well as languages in which the rejected snippet that I shared would be accepted). Finally, a question remains: is it safe to rely on the pattern I described or is it an undocumented anti-pattern that may result in an error in the future? To me, there is no way to answer this question based on the available documentation and my understanding of Julia's internals. I am happy to help improving the documentation on these matters if people deem it useful. |
That's great. I agree it is not obvious what such a recursive import would mean so more docs for that would be useful, indeed. |
Main changes Namespaces, export, import, using - explain namespaces, qualified symbol names, and export lists - consolidate examples where applicable - fix examples which were outdated after JuliaLang#25306 - distribute the “Namespace miscellanea” section into parts in the appropriate sections - break up the summary table and explain each case in detail with examples - subsection on various strategies to handle symbol conflicts - use “bring into the namespace/scope” instead of “import” in the text, as readers confuse it with `import` - explicitly document what happens with multiple `using` / `import` statements - add relevant style / best practices suggestions which are now widely used in the Julia ecosystem Submodules - discuss usage of `using ParentModule.SubModule` etc (relies on code loading) - add submodule examples where order matters, fixes JuliaLang#38011 (also another example by @rdeits [from Discourse](https://discourse.julialang.org/t/problem-with-using-in-submodules/42321/2)) - mention that submodules do not “inherit” scope from parent Misc incidental changes - in the Methods chapter, add a note about adding methods to functions in other modules - add a markdown id to the code-loading chapter The “Module initialization and precompilation” section is left unchanged.
* Reorganize the Modules chapter of the manual. Main changes Namespaces, export, import, using - explain namespaces, qualified symbol names, and export lists - consolidate examples where applicable - fix examples which were outdated after #25306 - distribute the “Namespace miscellanea” section into parts in the appropriate sections - break up the summary table and explain each case in detail with examples - subsection on various strategies to handle symbol conflicts - use “bring into the namespace/scope” instead of “import” in the text, as readers confuse it with `import` - explicitly document what happens with multiple `using` / `import` statements - add relevant style / best practices suggestions which are now widely used in the Julia ecosystem Submodules - discuss usage of `using ParentModule.SubModule` etc (relies on code loading) - add submodule examples where order matters, fixes #38011 (also another example by @rdeits [from Discourse](https://discourse.julialang.org/t/problem-with-using-in-submodules/42321/2)) - mention that submodules do not “inherit” scope from parent Misc incidental changes - in the Methods chapter, add a note about adding methods to functions in other modules - add a markdown id to the code-loading chapter The “Module initialization and precompilation” section is left unchanged. Co-authored-by: Tim Holy <[email protected]> Co-authored-by: Simon Byrne <[email protected]>
It is well documented how to use relative paths to import individual names that belong to a parent or sibling module.
However, the following code seems to be valid in Julia:
Here, it appears that the effect of having
using TestPackage
inSub
is to bring all exported names from TestPackage that are defined before Sub into scope. In the example above, this means thatx
is accessible in Sub buty
is not.Is this behavior documented somewhere though and would it be safe to rely on it?
The text was updated successfully, but these errors were encountered: