0

I'm trying to plot on a bar graph a year long set of values with Python/Pandas. The resulting graph is quite cluttered and my attempts to set xtick labels are not working.

My original code:

import datetime as dt
import random
import pandas as pd

#generate year-long list of dates
i = 0
list_of_dates = []
last_date = dt.date(2017, 1, 1)
while i < 365:
    list_of_dates.append(last_date)
    last_date += dt.timedelta(days=1)
    #print(last_date)
    i = i + 1

#generate random values for example
daily_rainfall = []
j = 0
while j < 365:
    daily_rainfall.append(random.randint(0,3))
    j = j + 1
    
#put lists in DF
rainfall_dataframe = pd.DataFrame(list(zip(list_of_dates, daily_rainfall)),columns=["Date","Precipitation"])
rainfall_dataframe = rainfall_dataframe.groupby(["Date"]).sum()

rainfall_dataframe.plot(kind="bar", figsize=(13,7))

returns this:

img1

Unusable, obviously. So I wanted it to only label x-ticks on a monthly basis. I tried creating a list of datetime date objects that was only the first of every month but when I try to pass this to df.plot() it returns nothing.

xlablist = []
xlablist.append(dt.date(2017, 1, 1))
xlablist.append(dt.date(2017, 6, 1))
xlablist.append(dt.date(2018, 1, 1))

rainfall_dataframe.plot(kind="bar", figsize=(13,7), xticks=xlablist)

returns:

img2

Please help!

1

2 Answers 2

1

One of possible solutions, using MonthLocator to specify where to put x labels and DateFormatter to specify the format of labels:

# Imports
import matplotlib.pyplot as plt
import matplotlib.dates as mdates

# Create source data
np.random.seed(0)
dates = pd.date_range(start='2017-01-01', end='2017-12-31')
rainfall = np.random.randint(0, 20, dates.size)

# Drawing
fig, ax = plt.subplots(figsize=(10, 4))
plt.xlabel('Month')
plt.ylabel('mm')
plt.title('Rainfall 2017')
ax.xaxis.set_major_locator(mdates.MonthLocator())
fmt = mdates.DateFormatter('%b %Y')
ax.xaxis.set_major_formatter(fmt)
ax.bar(dates, rainfall)
plt.setp(ax.get_xticklabels(), rotation=30);

For the above source data I got the following picture:

enter image description here

Sign up to request clarification or add additional context in comments.

Comments

0

You could use Date locators.

import datetime as dt
import random
import pandas as pd
import matplotlib.pyplot as plt
import matplotlib.dates as mdates


#generate year-long list of dates
i = 0
list_of_dates = []
last_date = dt.date(2017, 1, 1)
while i < 365:
    list_of_dates.append(last_date)
    last_date += dt.timedelta(days=1)
    #print(last_date)
    i = i + 1

#generate random values for example
daily_rainfall = []
j = 0
while j < 365:
    daily_rainfall.append(random.randint(0,3))
    j = j + 1
    
#put lists in DF
rainfall_dataframe = pd.DataFrame(list(zip(list_of_dates, daily_rainfall)),columns=["Date","Precipitation"])
rainfall_dataframe = rainfall_dataframe.groupby(["Date"]).sum()

rainfall_dataframe.plot(kind="bar", figsize=(13,7))

plt.gca().xaxis.set_major_locator(mdates.MonthLocator())

plt.xticks(rotation=45)

plt.show()

enter image description here

3 Comments

I tried running your code exactly in a fresh Jupyter Notebook and the xticks didn't show up. Is there a problem with my install of matplotlib or something?
I don't use Jupyter Notebook. Does it work on your Python IDLE?
@Krbin Does this official demo: Date tick labels work in your Jupyter Notebook?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.