-
Notifications
You must be signed in to change notification settings - Fork 2.7k
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
Expm typo fix add log #1271
Merged
Merged
Expm typo fix add log #1271
Conversation
This file contains 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
implemenation from remote. On branch main Your branch is behind 'origin/main' by 127 commits, and can be fast-forwarded. (use "git pull" to update your local branch) Changes to be committed: modified: qlib/data/ops.py Changes not staged for commit: modified: qlib/contrib/evaluate.py modified: qlib/contrib/strategy/signal_strategy.py modified: qlib/utils/__init__.py modified: qlib/workflow/cli.py modified: qlib/workflow/expm.py Untracked files: .idea/ ------------------------ >8 ------------------------ Do not modify or remove the line above. Everything below it will be ignored. diff --git a/qlib/data/ops.py b/qlib/data/ops.py index bdc032c0..23db25cc 100644 --- a/qlib/data/ops.py +++ b/qlib/data/ops.py @@ -32,6 +32,90 @@ except ValueError as e: np.seterr(invalid="ignore") +#################### Change instrument ######################## +# In some case, one may want to change to another instrument when calculating, for example +# calculate beta of a stock with respect to a market index +# this would require change the calculation of features from the stock (original instrument) to +# the index (reference instrument) +# ############################# + + +class ChangeInstrument(ExpressionOps): + """Change Instrument Operator + In some case, one may want to change to another instrument when calculating, for example, to + calculate beta of a stock with respect to a market index. + This would require changing the calculation of features from the stock (original instrument) to + the index (reference instrument) + Parameters + ---------- + instrument: new instrument for which the downstream operations should be performed upon. + i.e., SH000300 (CSI300 index), or ^GPSC (SP500 index). + + feature: the feature to be calculated for the new instrument. + Returns + ---------- + Expression + feature operation output + """ + + def __init__(self, instrument, feature): + self.instrument = instrument + self.feature = feature + + def __str__(self): + return "{}({},{})".format(type(self).__name__, self.instrument, self.feature) + + def load(self, instrument, start_index, end_index, freq): + """load feature + + Parameters + ---------- + instrument : str + instrument code, however, the actual instrument loaded is self.instrument through initialization + start_index : str + feature start index [in calendar]. + end_index : str + feature end index [in calendar]. + freq : str + feature frequency. + + Returns + ---------- + pd.Series + feature series: The index of the series is the calendar index + """ + from .cache import H # pylint: disable=C0415 + + # cache + args = str(self), self.instrument, start_index, end_index, freq + if args in H["f"]: + return H["f"][args] + if start_index is not None and end_index is not None and start_index > end_index: + raise ValueError("Invalid index range: {} {}".format(start_index, end_index)) + try: + series = self._load_internal(self.instrument, start_index, end_index, freq) + except Exception as e: + get_module_logger("data").debug( + f"Loading data error: instrument={instrument}, expression={str(self)}, " + f"start_index={start_index}, end_index={end_index}, freq={freq}. " + f"error info: {str(e)}" + ) + raise + series.name = str(self) + H["f"][args] = series + return series + + def _load_internal(self, instrument, start_index, end_index, freq): + series = self.feature.load(self.instrument, start_index, end_index, freq) + return series + + def get_longest_back_rolling(self): + return self.feature.get_longest_back_rolling() + + def get_extended_window_size(self): + return self.feature.get_extended_window_size() + + #################### Element-Wise Operator #################### @@ -1541,6 +1625,7 @@ class TResample(ElemOperator): TOpsList = [TResample] OpsList = [ + ChangeInstrument, Rolling, Ref, Max,
Thanks! |
qianyun210603
pushed a commit
to qianyun210603/qlib
that referenced
this pull request
Mar 23, 2023
* My own implementation of ChangeInstrument Op. There is a newer, simpler implemenation from remote. On branch main Your branch is behind 'origin/main' by 127 commits, and can be fast-forwarded. (use "git pull" to update your local branch) Changes to be committed: modified: qlib/data/ops.py Changes not staged for commit: modified: qlib/contrib/evaluate.py modified: qlib/contrib/strategy/signal_strategy.py modified: qlib/utils/__init__.py modified: qlib/workflow/cli.py modified: qlib/workflow/expm.py Untracked files: .idea/ ------------------------ >8 ------------------------ Do not modify or remove the line above. Everything below it will be ignored. diff --git a/qlib/data/ops.py b/qlib/data/ops.py index bdc032c0..23db25cc 100644 --- a/qlib/data/ops.py +++ b/qlib/data/ops.py @@ -32,6 +32,90 @@ except ValueError as e: np.seterr(invalid="ignore") +#################### Change instrument ######################## +# In some case, one may want to change to another instrument when calculating, for example +# calculate beta of a stock with respect to a market index +# this would require change the calculation of features from the stock (original instrument) to +# the index (reference instrument) +# ############################# + + +class ChangeInstrument(ExpressionOps): + """Change Instrument Operator + In some case, one may want to change to another instrument when calculating, for example, to + calculate beta of a stock with respect to a market index. + This would require changing the calculation of features from the stock (original instrument) to + the index (reference instrument) + Parameters + ---------- + instrument: new instrument for which the downstream operations should be performed upon. + i.e., SH000300 (CSI300 index), or ^GPSC (SP500 index). + + feature: the feature to be calculated for the new instrument. + Returns + ---------- + Expression + feature operation output + """ + + def __init__(self, instrument, feature): + self.instrument = instrument + self.feature = feature + + def __str__(self): + return "{}({},{})".format(type(self).__name__, self.instrument, self.feature) + + def load(self, instrument, start_index, end_index, freq): + """load feature + + Parameters + ---------- + instrument : str + instrument code, however, the actual instrument loaded is self.instrument through initialization + start_index : str + feature start index [in calendar]. + end_index : str + feature end index [in calendar]. + freq : str + feature frequency. + + Returns + ---------- + pd.Series + feature series: The index of the series is the calendar index + """ + from .cache import H # pylint: disable=C0415 + + # cache + args = str(self), self.instrument, start_index, end_index, freq + if args in H["f"]: + return H["f"][args] + if start_index is not None and end_index is not None and start_index > end_index: + raise ValueError("Invalid index range: {} {}".format(start_index, end_index)) + try: + series = self._load_internal(self.instrument, start_index, end_index, freq) + except Exception as e: + get_module_logger("data").debug( + f"Loading data error: instrument={instrument}, expression={str(self)}, " + f"start_index={start_index}, end_index={end_index}, freq={freq}. " + f"error info: {str(e)}" + ) + raise + series.name = str(self) + H["f"][args] = series + return series + + def _load_internal(self, instrument, start_index, end_index, freq): + series = self.feature.load(self.instrument, start_index, end_index, freq) + return series + + def get_longest_back_rolling(self): + return self.feature.get_longest_back_rolling() + + def get_extended_window_size(self): + return self.feature.get_extended_window_size() + + #################### Element-Wise Operator #################### @@ -1541,6 +1625,7 @@ class TResample(ElemOperator): TOpsList = [TResample] OpsList = [ + ChangeInstrument, Rolling, Ref, Max, * update expm.py * removed duplicate implementation for ChangeInstrument
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
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.
fixed a typo and added a logger.info to log more info.
Description
Motivation and Context
How Has This Been Tested?
pytest qlib/tests/test_all_pipeline.py
under upper directory ofqlib
.Screenshots of Test Results (if appropriate):
Types of changes