- What can I do about «ImportError: Cannot import name X» or «AttributeError: . (most likely due to a circular import)»?
- 17 Answers 17
- Python module cannot import name
- # ImportError: cannot import name X in Python [Solved]
- # Resolving circular import issues
- # Try to import the entire module
- # Make sure you don’t have spelling errors in import statements
- # Trying to import a member from a file that doesn’t export it
- # Trying to use a function that isn’t available in your version of Python
- # Shadowing a module with a local file with the same name
- # Restart the kernel in Jupyter Notebook
- # Conclusion
What can I do about «ImportError: Cannot import name X» or «AttributeError: . (most likely due to a circular import)»?
I have some code spread across multiple files that try to import from each other, as follows: main.py:
from physics import Physics class Ent: .
from entity import Ent class Physics: .
Traceback (most recent call last): File "main.py", line 2, in from entity import Ent File ". /entity.py", line 5, in from physics import Physics File ". /physics.py", line 2, in from entity import Ent ImportError: cannot import name Ent
I’m assume the error is due to importing entity twice — once in main.py and later in physics.py — but how can I work around the problem? See also What happens when using mutual or circular (cyclic) imports in Python? for a general overview of what is allowed and what causes a problem WRT circular imports. See Why do circular imports seemingly work further up in the call stack but then raise an ImportError further down? for technical details on why and how the problem occurs.
@jsells You should just call your classes Entity and Vector instead of Ent and Vect , there’s no reason to shorten such names. And yes, use import vector and then x = vector.Vector(0,0,0) .
Hey @Kevin since you know Java better, what is your impression of this 2008 article where the author’s first sentence refers to how circular dependencies are «pretty common practice» in Java ?
Every major language supports circular imports without a problem. C#, C, C++, Java, Objective-C. This isn’t 1991.
If you can’t get away from circular dependencies, you can import directly in the function or class where you need the particular dependency instead of global to the file
17 Answers 17
You have circular dependent imports. physics.py is imported from entity before class Ent is defined and physics tries to import entity that is already initializing. Remove the dependency to physics from entity module.
There is not much you can do than to refactor your code. If you do not refer Physics in Ent constructor definition move mport just under the Ent. If you do, add method like setPhysics to enable import after constructor.
While you should definitely avoid circular dependencies, you can defer imports in python.
import SomeModule def someFunction(arg): from some.dependency import DependentClass
this ( at least in some instances ) will circumvent the error.
I don’t really know all the details, but the fact that you have a circular import often means your code may be badly organized — and it can mask other issues. Better usually to try and split out the thing you’re trying to import into a separate module if you can and have both call sites import from there. With that said, I’ve done the above plenty of times myself, but it always ‘smelled bad’ 😉
This is a circular dependency. It can be solved without any structural modifications to the code. The problem occurs because in vector you demand that entity be made available for use immediately, and vice versa. The reason for this problem is that you asking to access the contents of the module before it is ready — by using from x import y . This is essentially the same as
Python is able to detect circular dependencies and prevent the infinite loop of imports. Essentially all that happens is that an empty placeholder is created for the module (ie. it has no content). Once the circularly dependent modules are compiled it updates the imported module. This is works something like this.
a = module() # import a # rest of module a.update_contents(real_a)
For python to be able to work with circular dependencies you must use import x style only.
import x class cls: def __init__(self): self.y = x.y
Since you are no longer referring to the contents of the module at the top level, python can compile the module without actually having to access the contents of the circular dependency. By top level I mean lines that will be executed during compilation as opposed to the contents of functions (eg. y = x.y ). Static or class variables accessing the module contents will also cause problems.
Python module cannot import name
Last updated: Feb 18, 2023
Reading time · 6 min
# ImportError: cannot import name X in Python [Solved]
The error «ImportError: cannot import name X» occurs for multiple reasons:
- Having circular imports between files.
- Misspelling the name of the function or class that is being imported or the name of the module you are importing from.
- Trying to import a function or class that isn’t available in the specified module, version of the module, or version of the Python interpreter (for standard libraries).
- Naming a file with the same name as a module you’re trying to import from, e.g. sys.py and then importing from the sys module.
The error often occurs when we have circular imports (importing members between the same files).
To solve the error, move the functions or classes to a third file and import them from a central location in other files.
# Resolving circular import issues
Here is an example of having circular imports (importing members between the same files).
This file is called main.py and imports a function from another.py .
Copied!from another import do_multiplication # 👈️ imports from another.py def do_addition(a, b): return a + b print(do_multiplication(5, 5))
And here is the code for another.py .
Copied!from main import do_addition # 👈️ imports from main.py def do_multiplication(a, b): return a * b # ⛔️ ImportError: cannot import name 'do_multiplication' from partially initialized module 'another' (most likely due to a circular import) (/home/borislav/Desktop/bobbyhadz_python/another.py) print(do_addition(5, 5))
We are importing members between the two files, so they depend on one another.
This is very confusing for the Python interpreter and should be avoided.
Instead, you can move the functions to a third file, and import them from a central location in your other files, without having to deal with circular imports.
Here is the updated code for third.py .
Copied!def do_addition(a, b): return a + b def do_multiplication(a, b): return a * b
And now we are able to import the two functions in any other file without having circular imports.
Copied!from third import do_addition, do_multiplication print(do_addition(5, 5)) # 👉️ 10 print(do_multiplication(5, 5)) # 👉️ 25
The another.py file can also import the functions from third.py without any issues.
Now the interpreter won’t get confused when running our code because we don’t have imports between the same files.
For example, if you have files a.py and b.py , move the objects in a file called c.py and import the objects from c.py to avoid any circular imports.
# Try to import the entire module
If the error persists, try to import the entire module, instead of importing a specific member from the module.
Copied!import math # ['__doc__', '__loader__', '__name__', '__package__', '__spec__', 'acos', 'acosh', 'asin', 'asinh', 'atan', 'atan2', 'atanh', 'cbrt', 'ceil', 'comb', 'copysign', 'cos', 'cosh', 'degrees', 'dist', 'e', 'erf', 'erfc', 'exp', 'exp2', 'expm1', 'fabs', 'factorial', 'floor', 'fmod', 'frexp', 'fsum', 'gamma', 'gcd', 'hypot', 'inf', 'isclose', 'isfinite', 'isinf', 'isnan', 'isqrt', 'lcm', 'ldexp', 'lgamma', 'log', 'log10', 'log1p', 'log2', 'modf', 'nan', 'nextafter', 'perm', 'pi', 'pow', 'prod', 'radians', 'remainder', 'sin', 'sinh', 'sqrt', 'tan', 'tanh', 'tau', 'trunc', 'ulp'] print(dir(math))
You can use the dir() function to print all of the attributes of the module and check if the member you are trying to import exists in the module.
You can also use your IDE to try to autocomplete when accessing specific members.
If autocomplete doesn’t automatically start, try pressing CTRL + Space on your keyboard.
If your IDE can’t help you with autocomplete, the member you are trying to access likely doesn’t exist in the module.
You can also try to autocomplete directly when importing the module.
For example, if you start typing from numpy import and press CTRL + Space to start autocomplete, your IDE should come up with suggestions of valid imports.
Copied!from numy import press CTRL + Space>
# Make sure you don’t have spelling errors in import statements
Carefully check your spelling as the names of functions, classes and modules are case-sensitive.
If you misspell the name of the function or class you’re trying to import, the error occurs.
For example, the following import statement causes the error.
Copied!# ImportError: cannot import name 'Array' from 'numpy' (/home/borislav/Desktop/bobbyhadz_python/venv/lib/python3.11/site-packages/numpy/__init__.py) from numpy import Array print(Array)
The error is caused because I tried to import Array (uppercase A ) from numpy and the function is actually named array (lowercase a ).
Copied!from numpy import array # ✅ works print(array)
Correcting the spelling error resolves the issue.
# Trying to import a member from a file that doesn’t export it
You might be trying to import a function or class from a module that doesn’t export it.
For example, you might have installed a version of the module in which the specified function doesn’t exist because it has been moved or completely removed.
- The module you are trying to import from exists.
- However, the member you are trying to import from the module doesn’t exist.
# Trying to use a function that isn’t available in your version of Python
The same could be the case for your specific version of Python.
A standard module might not contain the function you are trying to import because it is added in a later version or has been removed.
You can try to google around to see if the package you are importing from contains the function or class you are trying to import.
You can check your Python version with the python —version command if importing built-in modules.
Or you can check your version of a specific package with the pip show package-name command if importing from third-party modules.
Make sure to replace numpy with the name of the package you are importing from.
# Shadowing a module with a local file with the same name
Make sure you haven’t named a file in your project with the same name as the module you are trying to import from, e.g. numpy.py .
This would shadow the module you are trying to import from and is often a cause of the error.
Notice that there is a local file named numpy.py in the example.
When I try to import from the numpy module, the error is raised because Python only finds my local numpy file.
To resolve the error, rename your local file to not shadow the remote, third-party module.
When you have a local file with the same name as a global module you’re trying to import, the Python interpreter finds the local file first and exits.
For example, if you have a local file named example.py , you won’t be able to import from the example module because the Python interpreter will only be able to find your own example.py file when resolving the path.
# Restart the kernel in Jupyter Notebook
If the error persists and you use Jupyter Notebook, try restarting the kernel.
# Conclusion
To solve the «ImportError: cannot import name X» error, make sure:
- You don’t have any circular imports between your files.
- You haven’t misspelled the name of the function or class that is being imported or the name of the module you are importing from.
- You aren’t trying to import a function or class that isn’t available in the specified module, version of the module, or version of the Python interpreter (for standard libraries).
- You haven’t named a file in your project with the same name as a module you are trying to import from, e.g. sys.py .
I wrote a book in which I share everything I know about how to become a better, more efficient programmer.