From d0fdb0ac2ff41fb7e4f5f9ea9a13c1c0cd5ad3b1 Mon Sep 17 00:00:00 2001 From: "Roberto Gomes, PhD" <88116667+rgaveiga@users.noreply.github.com> Date: Sun, 14 Apr 2024 10:11:29 -0300 Subject: [PATCH] Correct README.md (#21) * Correct README.md * Change README.md after first review * Correct formatting of the naked call dict --- README.md | 199 +++++++++++++++++++++++++++++++----------------------- 1 file changed, 115 insertions(+), 84 deletions(-) diff --git a/README.md b/README.md index ffc87ab..c9049f1 100644 --- a/README.md +++ b/README.md @@ -1,25 +1,30 @@ # OptionLab -This package is a lightweight library written entirely in Python, designed to provide quick evaluation of -option strategies. - -The code produces various outputs, including the profit/loss profile of the strategy on a user-defined -target date, the range of stock prices for which the strategy is profitable (i.e., generating a return -greater than \$0.01), the Greeks associated with each leg of the strategy, the resulting debit or credit -on the trading account, the maximum and minimum returns within a specified lower and higher price range -of the underlying asset, and an estimate of the strategy's probability of profit. - -The probability of profit (PoP) for the strategy is calculated based on the distribution of estimated -prices of the underlying asset on the user-defined target date. Specifically, for the price range in the payoff -where the strategy generates profit, the PoP represents the probability that the stock price will fall within -that range. This distribution of underlying asset prices on the target date can be lognormal, log-Laplace, or -derived from the Black-Scholes model. Additionally, the distribution can be obtained through simulations -(e.g., Monte Carlo) or machine learning models. - -Despite the code having been developed with option strategies in mind, it can also be used for strategies -that combine options with stocks and/or take into account the profits or losses of closed trades. - -If you have any questions, corrections, comments or suggestions, just [drop a message](mailto:roberto.veiga@ufabc.edu.br). +This package is a lightweight library written entirely in Python, designed to provide +quick evaluation of option strategies. + +The code produces various outputs, including the profit/loss profile of the strategy on +a user-defined target date, the range of stock prices for which the strategy is +profitable (i.e., generating a return greater than \$0.01), the Greeks associated with +each leg of the strategy, the resulting debit or credit on the trading account, the +maximum and minimum returns within a specified lower and higher price range of the +underlying asset, and an estimate of the strategy's probability of profit. + +The probability of profit (PoP) for the strategy is calculated based on the distribution +of estimated prices of the underlying asset on the user-defined target date. +Specifically, for the price range in the payoff where the strategy generates profit, the +PoP represents the probability that the stock price will fall within that range. This +distribution of underlying asset prices on the target date can be lognormal, +log-Laplace, or derived from the Black-Scholes model. Additionally, the distribution can +be obtained through simulations (e.g., Monte Carlo) or machine learning models. + +Despite the code having been developed with option strategies in mind, it can also be +used for strategies that combine options with stocks and/or take into account the +profits or losses of closed trades. + +If you have any questions, corrections, comments or suggestions, just +[drop a message](mailto:roberto.veiga@ufabc.edu.br). + You can also reach me on [Linkedin](https://www.linkedin.com/in/roberto-gomes-phd-8a718317b/). ## Installation @@ -80,35 +85,41 @@ The input data passed to `model_validate` above needs to be of the following str - `compute_expectation` : logical, optional - Whether or not the strategy's average profit and loss must be computed from a numpy - array of random terminal prices generated from the chosen distribution. Default is False. + array of random terminal prices generated from the chosen distribution. Default is + False. - `discard_nonbusinessdays` : logical, optional - Whether to discard Saturdays and Sundays (and maybe holidays) when counting the number of days between two dates. Default is True. - `country` : string, optional - - Country for which the holidays will be considered if 'discard_nonbusinessdyas' is True. Default is 'US'. + - Country for which the holidays will be considered if 'discard_nonbusinessdays' is + True. Default is 'US'. - `start_date` : dt.date, optional - - Start date in the calculations. If not provided, days_to_target_date must be provided. + - Start date in the calculations. If not provided, days_to_target_date must be + provided. - `target_date` : dt.date, optional - - Start date in the calculations. If not provided, days_to_target_date must be provided. + - Target date in the calculations. If not provided, days_to_target_date must be + provided. - `days_to_target_date` : int, optional - - Days to maturity. If not provided, start_date and end_date must be provided. + - Number of days until the target date, typically the maturity date of the options. + If not provided, start_date and end_date must be provided. - `distribution` : string, optional - - Statistical distribution used to compute probabilities. It can be 'black-scholes', 'normal', - 'laplace' or 'array'. Default is 'black-scholes'. + - Statistical distribution used to compute probabilities. It can be 'black-scholes', + 'normal', 'laplace' or 'array'. Default is 'black-scholes'. - `mc_prices_number` : int, optional - - Number of random terminal prices to be generated when calculating the average profit and - loss of a strategy. Default is 100,000. + - Number of random terminal prices to be generated when calculating the average + profit and loss of a strategy. Default is 100,000. --- -The `strategy` attribute can have be either of type `OptionStrategy`, `StockStrategy`, or `ClosedPosition`. +The `strategy` attribute can be either of type `OptionStrategy`, `StockStrategy`, or +`ClosedPosition`. The `OptionStrategy` structure: @@ -130,20 +141,21 @@ The `OptionStrategy` structure: - Either 'buy' or 'sell'. It is mandatory. - `prev_pos` : float - - Premium effectively paid or received in a previously opened position. If positive, it - means that the position remains open and the payoff calculation takes this price into account, - not the current price of the option. If negative, it means that the position is closed and the - difference between this price and the current price is considered in the payoff calculation. + - Premium effectively paid or received in a previously opened position. If positive, + it means that the position remains open and the payoff calculation takes this price + into account, not the current price of the option. If negative, it means that the + position is closed and the difference between this price and the current price is + considered in the payoff calculation. - `expiration` : string | int - Expiration date or days to maturity. --- - + `StockStrategy`: --- - + - `type` : string - It must be 'stock'. It is mandatory. @@ -154,15 +166,17 @@ The `OptionStrategy` structure: - Either 'buy' or 'sell'. It is mandatory. - `prev_pos` : float - - Stock price effectively paid or received in a previously opened position. If positive, it - means that the position remains open and the payoff calculation takes this price into account, - not the current price of the stock. If negative, it means that the position is closed and the - difference between this price and the current price is considered in the payoff calculation. + - Stock price effectively paid or received in a previously opened position. If + positive, it means that the position remains open and the payoff calculation + takes this price into account, not the current price of the stock. If negative, it + means that the position is closed and the difference between this price and the + current price is considered in the payoff calculation. --- -For a non-determined previously opened position to be closed, which might consist of any combination of calls, -puts and stocks, the `ClosedPosition` must contain two keys: +For a non-determined previously opened position to be closed, which might consist +of any combination of calls, puts and stocks, the `ClosedPosition` must contain two +keys: --- @@ -170,13 +184,14 @@ puts and stocks, the `ClosedPosition` must contain two keys: - It must be 'closed'. It is mandatory. - `prev_pos` : float - - The total value of the position to be closed, which can be positive if it made a profit or negative if it is a loss. It is mandatory. + - The total value of the position to be closed, which can be positive if it made + a profit or negative if it is a loss. It is mandatory. --- -For example, let's say we wanted to calculate the probability of profit for naked calls on Apple stocks -with maturity on December 17, 2021. The strategy setup consisted of selling 100 175.00 strike -calls for 1.15 each on November 22, 2021. +For example, let's say we wanted to calculate the probability of profit for naked +calls on Apple stocks with maturity on December 17, 2021. The strategy setup consisted +of selling 100 175.00 strike calls for 1.15 each on November 22, 2021. ```python inputs_data = { @@ -188,12 +203,19 @@ inputs_data = { "min_stock": 120, "max_stock": 200, "strategy": [ - {"type": "call", "strike": 175.0, "premium": 1.15, "n": 100, "action": "sell"} + { + "type": "call", + "strike": 175.0, + "premium": 1.15, + "n": 100, + "action":"sell" + } ], } ``` -The calculations can be run by using: +The simplest way to perform the calculations is by calling the `run_strategy` function +as follows: ```python from optionlab import run_strategy @@ -201,8 +223,9 @@ from optionlab import run_strategy out = run_strategy(inputs_data) ``` -Alternatively, the inputs object can be passed to the `StrategyEngine` object and the calculations are performed by calling -the `run` method of the `StrategyEngine` object: +Alternatively, an `Inputs` object can be passed to the `StrategyEngine` object and +the calculations are performed by calling the `run` method of the `StrategyEngine` +object: ```python from optionlab import StrategyEngine @@ -211,7 +234,7 @@ st = StrategyEngine(Inputs.model_validate(inputs_data)) out = st.run() ``` -This method returns an `Outputs` object with the following structure: +In both cases, `out` contains an `Outputs` object with the following structure: --- @@ -219,7 +242,8 @@ This method returns an `Outputs` object with the following structure: - Probability of the strategy yielding at least $0.01. - `profit_ranges` : list - - A list of minimum and maximum stock prices defining ranges in which the strategy makes at least $0.01. + - A list of minimum and maximum stock prices defining ranges in which the strategy + makes at least $0.01. - `strategy_cost` : float - Total strategy cost. @@ -254,20 +278,24 @@ This method returns an `Outputs` object with the following structure: - `probability_of_profit_target` : float, optional - Probability of the strategy yielding at least the profit target. -- `project_target_ranges` : list, optional - - A list of minimum and maximum stock prices defining ranges in which the strategy makes at least the profit target. +- `profit_target_ranges` : list, optional + - A list of minimum and maximum stock prices defining ranges in which the strategy + makes at least the profit target. - `probability_of_loss_limit` : float, optional - Probability of the strategy losing at least the loss limit. - `average_profit_from_mc` : float, optional - - Average profit as calculated from Monte Carlo-created terminal stock prices for which the strategy is profitable. + - Average profit as calculated from Monte Carlo-created terminal stock prices for + which the strategy is profitable. - `average_loss_from_mc` : float, optional - - Average loss as calculated from Monte Carlo-created terminal stock prices for which the strategy ends in loss. + - Average loss as calculated from Monte Carlo-created terminal stock prices for + which the strategy ends in loss. - `probability_of_profit_from_mc` : float, optional - - Probability of the strategy yielding at least $0.01 as calculated from Monte Carlo-created terminal stock prices. + - Probability of the strategy yielding at least $0.01 as calculated from Monte + Carlo-created terminal stock prices. --- To obtain the probability of profit of the naked call example above: @@ -278,17 +306,15 @@ print("Probability of Profit (PoP): %.1f%%" % (out.probability_of_profit * 100.0 ## Contributions -Although functional, **OptionLab** is still in its early stages of development. The author has limited time available -to work on this library, which is why contributions from individuals with expertise in options and Python -programming are greatly appreciated. - ### Dev setup This repository uses `poetry` as a package manager. Install `poetry` as per the -[poetry docs](https://python-poetry.org/docs/#installing-with-pipx). It is recommended to install poetry version -1.4.0 if there are issues with the latest versions. +[poetry docs](https://python-poetry.org/docs/#installing-with-pipx). It is +recommended to install `poetry` version 1.4.0 if there are issues with the latest +versions. -Once poetry is installed, set up your virtual environment for the repo with the following: +Once `poetry` is installed, set up your virtual environment for the repository with +the following: ``` cd optionlab/ @@ -297,23 +323,26 @@ source venv/bin/activate poetry install ``` -That should install all your dependencies and make you ready to contribute. Please add tests for all new features and -bug fixes and make sure you are formatting with [black](https://github.com/psf/black). +That should install all your dependencies and make you ready to contribute. Please +add tests for all new features and bug fixes and make sure you are formatting +with [black](https://github.com/psf/black). Optionally, to use Jupyter, you can install it with: `pip install juypter`. #### Git Hooks -This repo uses git hooks. Git hooks are scripts that run automatically every time a particular event occurs in a -Git repository. These events can include committing, merging, and pushing, among others. Git hooks allow developers -to enforce certain standards or checks before actions are completed in the repository, enhancing the workflow -and code quality. +This repo uses git hooks. Git hooks are scripts that run automatically every time +a particular event occurs in a Git repository. These events can include committing, +merging, and pushing, among others. Git hooks allow developers to enforce certain +standards or checks before actions are completed in the repository, enhancing the +workflow and code quality. -The pre-commit framework is a tool that leverages Git hooks to run checks on the code before it is committed to the -repository. By using pre-commit, developers can configure various plugins or hooks that automatically check for -syntax errors, formatting issues, or even run tests on the code being committed. This ensures that only code -that passes all the defined checks can be added to the repository, helping to maintain code quality and prevent -issues from being introduced. +The pre-commit framework is a tool that leverages Git hooks to run checks on the +code before it is committed to the repository. By using pre-commit, developers can +configure various plugins or hooks that automatically check for syntax errors, +formatting issues, or even run tests on the code being committed. This ensures that +only code that passes all the defined checks can be added to the repository, helping +to maintain code quality and prevent issues from being introduced. To install the pre-commit framework on a system with Homebrew, follow these steps: @@ -321,27 +350,29 @@ To install the pre-commit framework on a system with Homebrew, follow these step brew install pre-commit ``` -Once pre-commit is installed, navigate to the root directory of your Git repository where you want to -enable pre-commit hooks. Then, run the following command to set up pre-commit for that repository. This -command installs the Git hook scripts that the pre-commit framework will use to run checks before commits. +Once pre-commit is installed, navigate to the root directory of your Git repository +where you want to enable pre-commit hooks. Then, run the following command to set up +pre-commit for that repository. This command installs the Git hook scripts that the +pre-commit framework will use to run checks before commits. ``` pre-commit install ``` -Now, before each commit, the pre-commit hooks you've configured will automatically run. If any hook fails, -the commit will be aborted, allowing you to fix the issues before successfully committing your changes. This -process helps maintain a high code quality and ensures that common issues are addressed early in +Now, before each commit, the pre-commit hooks you've configured will automatically +run. If any hook fails, the commit will be aborted, allowing you to fix the issues +before successfully committing your changes. This process helps maintain a high code +quality and ensures that common issues are addressed early in the development process. To check all files in a repository with pre-commit, use: ``` pre-commit run --all-files - ``` ## Disclaimer -This is free software and is provided as is. The author makes no guarantee that its results are accurate and is -not responsible for any losses caused by the use of the code. Bugs can be reported as issues. +This is free software and is provided as is. The author makes no guarantee that its +results are accurate and is not responsible for any losses caused by the use of the +code. Bugs can be reported as issues.