I already have the code in which it gets the information and turns it into JSON.
I am not sure how to retrieve the median and average conversion rates and have them print on the screen with the the conversion rates.
#import libraries to handle request to api
import requests
import json
import pprint
import pandas as pd
import matplotlib.pyplot as plt
#base currency or reference currency
base="USD"
#required currency for plot
out_curr="ILS"
#exchange data from a date
start_date="2020-01-01"
#exchange data till a date
end_date="2021-12-31"
#api url for request
url = 'https://api.exchangerate.host/timeseries?base={0}&start_date={1}&end_date={2}&symbols={3}'.format(base,start_date,end_date,out_curr)
response = requests.get(url)
#retrive response in json format
data = response.json()
pprint.pprint(data["rates"])
#create an empty array to store date and exchange rates
rates=[]
#extract dates and rates from each item of dictionary or json in the above created list
for i, j in data["rates"].items():
rates.append([i, j[out_curr]])
print(rates)
#create an data frame
import pandas as pd
df=pd.DataFrame(rates)
#define column names explicitely
df.columns=["date","rate"]
df
#Put dates on the x-axis
x = df['date']
#Put exchange rates on the y-axis
y = df['rate']
#Specify the width and height of a figure in unit inches
fig = plt.figure(figsize=(15, 6))
#Rotate the date ticks on the x-axis by degrees
plt.xticks(rotation=90)
#Set title on the axis
plt.xlabel('Date', fontsize=12)
plt.ylabel('Exchange Rates', fontsize=12)
#Plot the data
plt.plot(x,y)
plt.show()
I'm unable find a way to show that information.
Related
I have a data set with prices of 6 major stocks i.e., Google, Amazon etc.
My plan is to create a plot which would show a percent change, pct_change()of column known as close_value.
As you can see my ticker_symbol is an object. I tried and changed it to float because of the string error but then I lost all ticker names i.e. I executed returns.close_value.plot();.
How not to lose stock names while plotting?
Data display
Data info
Does this work?
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
# Create Sample DataFrame
df1 = pd.DataFrame({'day_date': ['2020-05-28', '2020-05-27', '2020-05-26', '2020-05-22'],
'ticker_symbol': ['AAPL', 'AAPL','TSLA','TSLA'],
'close_value': [318, 400, 500, 450]})
# Convert to Timestamp format
df1['day_date'] = pd.to_datetime(df1['day_date'])
# Store % Change in new Column
df1['pct_change_close_value'] = df1['close_value'].pct_change()
# Fill null value with 0
df1['pct_change_close_value'].fillna(0, inplace = True)
# Display
display(df1)
# Check Data types of columns
display(df1.dtypes)
# Use Seaborn to plot
sns.lineplot(data = df1, x = 'day_date', y = 'pct_change_close_value', hue = 'ticker_symbol')
You just need to set hue = ticker_symbol in sns plot.
I have a time series data like below where the data consists of year and week. So, the data is from 2014 1st week to 2015 52 weeks.
Now, below is the line plot of the above mentioned data
As you can see the x axis labelling is not quite what I was trying to achieve since the point after 201453 should be 201501 and there should not be any straight line and it should not be up to 201499. How can I rescale the xaxis exactly according to Due_date column? Below is the code
rand_products = np.random.choice(Op_2['Sp_number'].unique(), 3)
selected_products = Op_2[Op_2['Sp_number'].isin(rand_products)][['Due_date', 'Sp_number', 'Billing']]
plt.figure(figsize=(20,10))
plt.grid(True)
g = sns.lineplot(data=selected_products, x='Due_date', y='Billing', hue='Sp_number', ci=False, legend='full', palette='Set1');
the issue is because 201401... etc. are read as numbers and that is the reason the line chart has that gap. To fix it, you will need to change the numbers to date format and plot it.
As the full data is not available, below is the two column dataframe which has the Due_date in the form of integer YYYYWW. Billing column is a bunch of random numbers. Use the method here to convert the integers to dateformat and plot. The gap will be removed....
import numpy as np
import pandas as pd
import random
import matplotlib.pyplot as plt
import seaborn as sns
Due_date = list(np.arange(201401,201454)) #Year 2014
Due_date.extend(np.arange(201501,201553)) #Year 2915
Billing = random.sample(range(500, 1000), 105) #billing numbers
df = pd.DataFrame({'Due_date': Due_date, 'Billing': Billing})
df.Due_date = df.Due_date.astype(str)
df.Due_date = pd.to_datetime(df['Due_date']+ '-1',format="%Y%W-%w") #Convert to date
plt.figure(figsize=(20,10))
plt.grid(True)
ax = sns.lineplot(data=df, x='Due_date', y='Billing', ci=False, legend='full', palette='Set1')
Output graph
I have a graph that shows the closing price of a stock throughout a day at each five minute interval. The x axis shows the time and the range of x values is from 9:30 to 4:00 (16:00).
The problem is that the automatic bounds for the x axis go from 9:37 to 16:07 and I really just want it from 9:30 to 16:00.
The code I am currently running is this:
stk = yf.Ticker(ticker)
his = stk.history(interval="5m", start=start, end=end).values.tolist() #open - high - low - close - volume
x = []
y = []
count = 0
five_minutes = datetime.timedelta(minutes = 5)
for bar in his:
x.append((start + five_minutes * count))#.strftime("%H:%M"))
count = count + 1
y.append(bar[3])
plt.clf()
plt.gca().xaxis.set_major_formatter(mdates.DateFormatter("%H:%M"))
plt.gca().xaxis.set_major_locator(mdates.MinuteLocator(interval=30))
plt.plot(x, y)
plt.gcf().autofmt_xdate()
plt.show()
And it produces this plot (currently a link because I am on a new user account):
I thought I was supposed to use the axis.set_data_interval function providing, so I did so by providing datetime objects representing 9:30 and 16:00 as the min and the max. This gave me the error:
TypeError: '<' not supported between instances of 'float' and 'datetime.datetime'
Is there another a way for me to be able to adjust the first xtick and still have it automatically fill in the rest?
This problem can be fixed by adjusting the way you use the mdates tick locator. Here is an example based on the one shared by r-beginners to make it comparable. Note that I use the pandas plotting function for convenience. The x_compat=True argument is needed for it to work with mdates:
import pandas as pd # 1.1.3
import yfinance as yf # 0.1.54
import matplotlib.dates as mdates # 3.3.2
# Import data
ticker = 'AAPL'
stk = yf.Ticker(ticker)
his = stk.history(period='1D', interval='5m')
# Create pandas plot with appropriately formatted x-axis ticks
ax = his.plot(y='Close', x_compat=True, figsize=(10,5))
ax.xaxis.set_major_locator(mdates.MinuteLocator(byminute=[0, 30]))
ax.xaxis.set_major_formatter(mdates.DateFormatter('%H:%M', tz=his.index.tz))
ax.legend(frameon=False)
ax.figure.autofmt_xdate(rotation=0, ha='center')
The sample data was created by obtaining Apple's stock price from Yahoo Finance. The desired five-minute interval labels are a list of strings obtained by using the date function to get the start and end times at five-minute intervals.
Based on this, the x-axis is drawn as a graph of the number of five-minute intervals and the closing price, and the x-axis is set to any interval by slicing.
import yfinance as yf
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
import pandas as pd
import numpy as np
ticker = 'AAPL'
stk = yf.Ticker(ticker)
his = stk.history(period='1D',interval="5m")
his.reset_index(inplace=True)
time_rng = pd.date_range('09:30','15:55', freq='5min')
labels = ['{:02}:{:02}'.format(t.hour,t.minute) for t in time_rng]
fig, ax = plt.subplots()
x = np.arange(len(his))
y = his.Close
ax.plot(x,y)
ax.set_xticks(x[::3])
ax.set_xticklabels(labels[::3], rotation=45)
plt.show()
I am working on a project to create an algorithmic trader. However, I want to remove the weekends from my data frame as it ruins the data as shown in I have tried to do somethings I found on StackOverflow but I get an error that the type is Timestamp and so I can't use that technique. It also isn't a column in the data frame. I'm new to python so I'm not very sure but I think it's an index since when I go through the .index function it shows me the date and time. I'm sorry if these are stupid questions but I am new to python and pandas.
Here is my code:
#import all the libraries
import nsetools as ns
import pandas as pd
import numpy
import matplotlib.pyplot as plt
from datetime import datetime
import yfinance as yf
plt.style.use('fivethirtyeight')
a = input("Enter the ticker name you wish to apply strategy to")
ticker = yf.Ticker(a)
hist = ticker.history(period="1mo", interval="15m")
print(hist)
plt.figure(figsize=(12.5, 4.5))
plt.plot(hist['Close'], label=a)
plt.title('close price history')
plt.xlabel("13 Nov 2020 too 13 Dec 2020")
plt.ylabel("Close price")
plt.legend(loc='upper left')
plt.show()
EDIT: On the suggestion of a user, I tried to modify my code to this
refinedlist = hist[hist.index.dayofweek<5]plt.style.use('fivethirtyeight')
a = input("Enter the ticker name you wish to apply strategy to")
ticker = yf.Ticker(a)
hist = ticker.history(period="1mo", interval="15m")
refinedlist = hist[hist.index.dayofweek<5]
print (refinedlist)
And graphed that, but the graph still includes the weekends on the x axis.
In the first place, stock market data does not exist because the market is closed on holidays and national holidays. The reason for this is that your unit of acquisition is time, so there is also no data from the time the market closes to the time it opens the next day.
For example, I graphed the first 50 results. (The x-axis doesn't seem to be correct.)
plt.plot(hist['Close'][:50], label=a)
As one example, if you include holidays and national holidays and draw a graph with missing values for the times when the market is not open, you get the following.
new_idx = pd.date_range(hist.index[0], hist.index[-1], freq='15min')
hist = hist.reindex(new_idx, fill_value=np.nan)
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from datetime import datetime
import yfinance as yf
# plt.style.use('fivethirtyeight')
# a = input("Enter the ticker name you wish to apply strategy to")
a = 'AAPL'
ticker = yf.Ticker(a)
hist = ticker.history(period="1mo", interval="15m")
new_idx = pd.date_range(hist.index[0], hist.index[-1], freq='15min')
hist = hist.reindex(new_idx, fill_value=np.nan)
plt.figure(figsize=(12.5, 4.5))
plt.plot(hist['Close'], label=a)
plt.title('close price history')
plt.xlabel("13 Nov 2020 too 13 Dec 2020")
plt.ylabel("Close price")
plt.legend(loc='upper left')
plt.show()
I am trying to manually create a candlestick chart with matplotlib using errorbar for the daily High and Low prices and Rectangle() for the Adjusted Close and Open prices. This question seemed to have all the prerequisites for accomplishing this.
I attempted to use the above very faithfully, but the issue of plotting something over an x-axis of datetime64[ns]'s gave me no end of errors, so I've additionally tried to incorporate the advice here on plotting over datetime.
This is my code so far, with apologies for the messiness:
import pandas as pd
import datetime as dt
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
from matplotlib.collections import PatchCollection
from matplotlib.patches import Rectangle
def makeCandles(xdata,high,low,adj_close,adj_open,fc='r',ec='None',alpha=0.5):
## Converting datetimes to numerical format matplotlib can understand.
dates = mdates.date2num(xdata)
## Creating default objects
fig,ax = plt.subplots(1)
## Creating errorbar peaks based on high and low prices
avg = (high + low) / 2
err = [high - avg,low - avg]
ax.errorbar(dates,err,fmt='None',ecolor='k')
## Create list for all the error patches
errorboxes = []
## Loop over data points; create "body" of candlestick
## based on adjusted open and close prices
errors=np.vstack((adj_close,adj_open))
errors=errors.T
for xc,yc,ye in zip(dates,avg,errors):
rect = Rectangle((xc,yc-ye[0]),1,ye.sum())
errorboxes.append(rect)
## Create patch collection with specified colour/alpha
pc = PatchCollection(errorboxes,facecolor=fc,alpha=alpha,edgecolor=ec)
## Add collection to axes
ax.add_collection(pc)
plt.show()
With my data looking like
This is what I try to run, first getting a price table from quandl,
import quandl as qd
api = '1uRGReHyAEgwYbzkPyG3'
qd.ApiConfig.api_key = api
data = qd.get_table('WIKI/PRICES', qopts = { 'columns': ['ticker', 'date', 'high','low','adj_open','adj_close'] }, \
ticker = ['AMZN', 'XOM'], date = { 'gte': '2014-01-01', 'lte': '2016-12-31' })
data.reset_index(inplace=True,drop=True)
makeCandles(data['date'],data['high'],data['low'],data['adj_open'],data['adj_close'])
The code runs with no errors, but outputs an empty graph. So what I am asking for is advice on how to plot these rectangles over the datetime dates. For the width of the rectangles, I simply put a uniform "1" bec. I am not aware of a simple way to specify the datetime width of a rectangle.
Edit
This is the plot I am currently getting, having transformed my xdata into matplotlib mdates:
Before I transformed xdata via mdates, with just xdata as my x-axis everywhere, this was one of the errors I kept getting:
To get the plot you want, there's a couple of things that need to be considered. First you're retrieving to stocks AMZN and XOM, displaying both will make the chart you want look funny, because the data are quite far apart. Second, candlestick charts in which you plot each day for several years will get very crowded. Finally, you need to format your ordinal dates back on the x-axis.
As mentioned in the comments, you can use the pre-built matplotlib candlestick2_ohlc function (although deprecated) accessible through mpl_finance, install as shown in this answer. I opted for using solely the matplotlib barchart with built-in errorbars.
import matplotlib.pyplot as plt
import matplotlib.dates as mdates
import quandl as qd
from matplotlib.dates import DateFormatter, WeekdayLocator, \
DayLocator, MONDAY
# get data
api = '1uRGReHyAEgwYbzkPyG3'
qd.ApiConfig.api_key = api
data = qd.get_table('WIKI/PRICES', qopts={'columns': ['ticker', 'date', 'high', 'low', 'open', 'close']},
ticker=['AMZN', 'XOM'], date={'gte': '2014-01-01', 'lte': '2014-03-10'})
data.reset_index(inplace=True, drop=True)
fig, ax = plt.subplots(figsize = (10, 5))
data['date'] = mdates.date2num(data['date'].dt.to_pydatetime()) #convert dates to ordinal
tickers = list(set(data['ticker'])) # unique list of stock names
for stock_ind in tickers:
df = data[data['ticker'] == 'AMZN'] # select one, can do more in a for loop, but it will look funny
inc = df.close > df.open
dec = df.open > df.close
ax.bar(df['date'][inc],
df['open'][inc]-df['close'][inc],
color='palegreen',
bottom=df['close'][inc],
# this yerr is confusing when independent error bars are drawn => (https://matplotlib.org/api/pyplot_api.html#matplotlib.pyplot.errorbar)
yerr = [df['open'][inc]-df['high'][inc], -df['open'][inc]+df['low'][inc]],
error_kw=dict(ecolor='gray', lw=1))
ax.bar(df['date'][dec],
df['close'][dec]-df['open'][dec],
color='salmon', bottom=df['open'][dec],
yerr = [df['close'][dec]-df['high'][dec], -df['close'][dec]+df['low'][dec]],
error_kw=dict(ecolor='gray', lw=1))
ax.set_title(stock_ind)
#some tweaking, setting the dates
mondays = WeekdayLocator(MONDAY) # major ticks on the mondays
alldays = DayLocator() # minor ticks on the days
weekFormatter = DateFormatter('%b %d') # e.g., Jan 12
dayFormatter = DateFormatter('%d') # e.g., 12
ax.xaxis.set_major_locator(mondays)
ax.xaxis.set_minor_locator(alldays)
ax.xaxis.set_major_formatter(weekFormatter)
ax.set_ylabel('monies ($)')
plt.show()