-
-
Notifications
You must be signed in to change notification settings - Fork 18.4k
TYP: core.computations.scope #29667
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
Closed
Closed
TYP: core.computations.scope #29667
Changes from all commits
Commits
Show all changes
4 commits
Select commit
Hold shift + click to select a range
286c186
annotations for Scope
jbrockmendel a0fe60a
privatize update
jbrockmendel 6fdb0d7
Merge branch 'master' of https://github.com/pandas-dev/pandas into cl…
jbrockmendel 10dc615
Merge branch 'master' of https://github.com/pandas-dev/pandas into cl…
jbrockmendel File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,24 +1,24 @@ | ||
""" | ||
Module for scope operations | ||
""" | ||
|
||
import datetime | ||
import inspect | ||
from io import StringIO | ||
import itertools | ||
import pprint | ||
import struct | ||
import sys | ||
from typing import Any, List, MutableMapping | ||
|
||
import numpy as np | ||
|
||
from pandas._libs.tslibs import Timestamp | ||
from pandas.compat.chainmap import DeepChainMap | ||
|
||
|
||
def _ensure_scope( | ||
level, global_dict=None, local_dict=None, resolvers=(), target=None, **kwargs | ||
): | ||
def ensure_scope( | ||
level: int, global_dict=None, local_dict=None, resolvers=(), target=None, **kwargs | ||
) -> "Scope": | ||
"""Ensure that we are grabbing the correct scope.""" | ||
return Scope( | ||
level + 1, | ||
|
@@ -104,22 +104,28 @@ class Scope: | |
""" | ||
|
||
__slots__ = ["level", "scope", "target", "resolvers", "temps"] | ||
level: int | ||
scope: DeepChainMap | ||
resolvers: DeepChainMap | ||
temps: MutableMapping[str, Any] | ||
|
||
def __init__( | ||
self, level, global_dict=None, local_dict=None, resolvers=(), target=None | ||
self, level: int, global_dict=None, local_dict=None, resolvers=(), target=None, | ||
): | ||
self.level = level + 1 | ||
|
||
# shallow copy because we don't want to keep filling this up with what | ||
# was there before if there are multiple calls to Scope/_ensure_scope | ||
# was there before if there are multiple calls to Scope/ensure_scope | ||
self.scope = DeepChainMap(_DEFAULT_GLOBALS.copy()) | ||
self.target = target | ||
|
||
assert all(isinstance(x, str) for x in self.scope), self.scope | ||
|
||
if isinstance(local_dict, Scope): | ||
self.scope.update(local_dict.scope) | ||
if local_dict.target is not None: | ||
self.target = local_dict.target | ||
self.update(local_dict.level) | ||
self._update(local_dict.level) | ||
|
||
frame = sys._getframe(self.level) | ||
|
||
|
@@ -161,7 +167,7 @@ def has_resolvers(self) -> bool: | |
""" | ||
return bool(len(self.resolvers)) | ||
|
||
def resolve(self, key, is_local): | ||
def resolve(self, key: str, is_local: bool): | ||
""" | ||
Resolve a variable name in a possibly local context. | ||
|
||
|
@@ -203,7 +209,7 @@ def resolve(self, key, is_local): | |
|
||
raise UndefinedVariableError(key, is_local) | ||
|
||
def swapkey(self, old_key, new_key, new_value=None): | ||
def swapkey(self, old_key: str, new_key: str, new_value=None): | ||
""" | ||
Replace a variable name, with a potentially new value. | ||
|
||
|
@@ -216,10 +222,14 @@ def swapkey(self, old_key, new_key, new_value=None): | |
new_value : object | ||
Value to be replaced along with the possible renaming | ||
""" | ||
maps: List[MutableMapping] | ||
mapping: MutableMapping | ||
|
||
# TODO: convince mypy that these maps are in fact mutable | ||
if self.has_resolvers: | ||
maps = self.resolvers.maps + self.scope.maps | ||
maps = self.resolvers.maps + self.scope.maps # type: ignore | ||
else: | ||
maps = self.scope.maps | ||
maps = self.scope.maps # type: ignore | ||
|
||
maps.append(self.temps) | ||
|
||
|
@@ -228,7 +238,7 @@ def swapkey(self, old_key, new_key, new_value=None): | |
mapping[new_key] = new_value | ||
return | ||
|
||
def _get_vars(self, stack, scopes): | ||
def _get_vars(self, stack, scopes: List[str]): | ||
""" | ||
Get specifically scoped variables from a list of stack frames. | ||
|
||
|
@@ -241,17 +251,17 @@ def _get_vars(self, stack, scopes): | |
evaluate to a dictionary. For example, ('locals', 'globals') | ||
""" | ||
variables = itertools.product(scopes, stack) | ||
for scope, (frame, _, _, _, _, _) in variables: | ||
for name, (frame, _, _, _, _, _) in variables: | ||
try: | ||
d = getattr(frame, "f_" + scope) | ||
d = getattr(frame, "f_" + name) | ||
self.scope = self.scope.new_child(d) | ||
finally: | ||
# won't remove it, but DECREF it | ||
# in Py3 this probably isn't necessary since frame won't be | ||
# scope after the loop | ||
del frame | ||
|
||
def update(self, level: int): | ||
def _update(self, level: int): | ||
""" | ||
Update the current scope by going back `level` levels. | ||
|
||
|
@@ -303,7 +313,7 @@ def ntemps(self) -> int: | |
return len(self.temps) | ||
|
||
@property | ||
def full_scope(self): | ||
def full_scope(self) -> DeepChainMap: | ||
""" | ||
Return the full scope for use with passing to engines transparently | ||
as a mapping. | ||
|
@@ -313,5 +323,6 @@ def full_scope(self): | |
vars : DeepChainMap | ||
All variables in this scope. | ||
""" | ||
maps = [self.temps] + self.resolvers.maps + self.scope.maps | ||
# TODO: convince mypy that all of the maps are mutable | ||
maps = [self.temps] + self.resolvers.maps + self.scope.maps # type: ignore | ||
Comment on lines
+326
to
+327
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. i think we could lose the ignore here using unpacking instead. diff --git a/pandas/core/computation/scope.py b/pandas/core/computation/scope.py
index 9b9dde83f..935b35e22 100644
--- a/pandas/core/computation/scope.py
+++ b/pandas/core/computation/scope.py
@@ -323,6 +323,4 @@ class Scope:
vars : DeepChainMap
All variables in this scope.
"""
- # TODO: convince mypy that all of the maps are mutable
- maps = [self.temps] + self.resolvers.maps + self.scope.maps # type: ignore
- return DeepChainMap(*maps)
+ return DeepChainMap(self.temps, *self.resolvers.maps, *self.scope.maps)
|
||
return DeepChainMap(*maps) |
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this could be a typeshed issue not a mypy issue as new_child should return type of self not
typing.ChainMap[_KT, _VT]
see https://github.com/python/typeshed/blob/34d68ab0a2117a08fa221d3a10884f35cacf2cdc/stdlib/3/collections/__init__.pyi#L323-L338There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the
# type: ignore
could be avoided with