# Untitled

unknown
python
a year ago
4.2 kB
0
Indexable
Never
```#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Wed Feb 22 17:01:07 2023

@author: noahakesson
"""

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns
from datetime import datetime

df = df.rename(columns={'PX_LAST':'price'})

# Define the rolling window size
window_size = 365

# Calculate the momentum for each stock
df['Momentum'] = df.groupby('Symbol')['esg'].apply(lambda x: x.pct_change(window_size).shift(-window_size))

# Define the threshold for buying and selling
sell_threshold = -0.05

# Initialize the portfolio
portfolio = pd.DataFrame(columns=['Symbol', 'Shares', 'Price', 'Total'])

# Initialize the statistics
statistics = pd.DataFrame(columns=['Symbol', 'Total Return', 'Annualized Return', 'Volatility'])

# Loop through each stock in the data
for symbol in df['Symbol'].unique():

# Filter the data for the current stock
stock_data = df[df['Symbol'] == symbol].copy()

# Apply the momentum strategy
stock_data['Signal'] = np.where(stock_data['Momentum'] > buy_threshold, 1, np.where(stock_data['Momentum'] < sell_threshold, -1, 0))
stock_data['Position'] = stock_data['Signal'].shift(1)
stock_data['Position'].fillna(0, inplace=True)

# Calculate the daily returns
stock_data['Returns'] = stock_data['price'].pct_change() * stock_data['Position']
stock_data['Cumulative Returns'] = (1 + stock_data['Returns']).cumprod()

# Calculate the portfolio value
shares = 10000 // stock_data['price'][0]
portfolio_data = pd.DataFrame({'Symbol': [symbol], 'Shares': [shares], 'Price': [stock_data['price'][0]], 'Total': [shares * stock_data['price'][0]]})
for i, row in stock_data.iterrows():
if row['Position'] == 1:
portfolio_data = portfolio_data.append({'Symbol': symbol, 'Shares': shares, 'Price': row['price'], 'Total': shares * row['price']}, ignore_index=True)
elif row['Position'] == -1:
portfolio_data = portfolio_data.append({'Symbol': symbol, 'Shares': -shares, 'Price': row['price'], 'Total': -shares * row['price']}, ignore_index=True)
portfolio_data['Cumulative Total'] = portfolio_data['Total'].cumsum()
portfolio = pd.concat([portfolio, portfolio_data])

# Calculate the statistics
total_return = None
annualized_return = None
volatility = None
print(symbol + str(len(portfolio_data['Cumulative Total'])))

if len(portfolio_data['Cumulative Total']) > 0:
total_return = (portfolio_data.loc['Cumulative Total',-1] - portfolio_data['Cumulative Total'][0]) / portfolio_data['Cumulative Total'][0]
annualized_return = (1 + total_return) ** (252 / len(stock_data)) - 1
volatility = stock_data['Returns'].std() * np.sqrt(252)
statistics = statistics.append({'Symbol': symbol, 'Total Return': total_return, 'Annualized Return': annualized_return, 'Volatility': volatility}, ignore_index=True)
else:
print(symbol)

# Calculate the overall portfolio value
portfolio['Cumulative Total'] = portfolio['Total'].cumsum()

# Plot the cumulative returns of each stock
sns.set(style='darkgrid')
g = sns.relplot(x='Date', y='Cumulative Returns', hue='Symbol', kind='line', data=df, height=6, aspect=2)
g.fig.suptitle('Cumulative Returns of Each Stock')
plt.show()

# Plot the portfolio value over time
sns.set(style='darkgrid')
plt.plot(portfolio.index, portfolio['Cumulative Total'])
plt.title('Portfolio Value Over Time')
plt.xlabel('Date')
plt.ylabel('Value')
plt.show()

# Plot the performance statistics of each stock
sns.set(style='darkgrid')
g = sns.catplot(x='Symbol', y='Annualized Return', kind='bar', data=statistics, height=6, aspect=2)
g.fig.suptitle('Annualized Return of Each Stock')
plt.show()

sns.set(style='darkgrid')
g = sns.catplot(x='Symbol', y='Volatility', kind='bar', data=statistics, height=6, aspect=2)
g.fig.suptitle('Volatility of Each Stock')
plt.show()

sns.set(style='darkgrid')
g = sns.catplot(x='Symbol', y='Total Return', kind='bar', data=statistics, height=6, aspect=2)
g.fig.suptitle('Total Return of Each Stock')
plt.show()```