-
-
Notifications
You must be signed in to change notification settings - Fork 1.2k
Open
Labels
False Negative π¦No message is emitted but something is wrong with the codeNo message is emitted but something is wrong with the codeNeeds decision πNeeds a decision before implemention or rejectionNeeds a decision before implemention or rejection
Milestone
Description
Current problem
The following code may not print what you expect on the last line:
from collections import defaultdict
errors = [
Exception("E101", "Boom!"),
Exception("E101", "Bam!"),
Exception("E102", "Shazam!"),
]
errors_per_arg0 = defaultdict(list)
for error in errors:
errors_per_arg0[error.args[0]].append(error)
for arg0, errors in errors_per_arg0.items():
print(arg0, "count:", len(errors))
print(errors)
The issue comes from the for
loop, where the errors
loop variable shadows the previously defined list.
The unexpected problem is that, on the last line, errors
is now a 1-item list!
There is this script output:
E101 count: 2
E102 count: 1
[Exception('E102', 'Shazam!')]
As far as I know, Pylint currently does not have any rule that detects this (tested using Pylint 2.17.3 & 3.0.0a6).
redefined-outer-name
for example, does not get triggered.
Desired solution
First, I'd like to know what Pylint maintainers think to be the best approach:
- improve the existing
redefined-outer-name
to cover this - introduce a new rule to detect this case
Additional context
There are some edge cases to consider when such case happens, where the definition of loop variable "erases" a variable in the current scope:
- if this variable is not used after the loop, should an error be raised?
- if this variable is re-assigned after the loop, before being read, should an error be raised?
Metadata
Metadata
Assignees
Labels
False Negative π¦No message is emitted but something is wrong with the codeNo message is emitted but something is wrong with the codeNeeds decision πNeeds a decision before implemention or rejectionNeeds a decision before implemention or rejection