Home > OS >  Remove unnecessary final month from x-axis tick
Remove unnecessary final month from x-axis tick

Time:08-02

I am plotting daily coal production data of 4 years, from 2019 to 2022, and using sequential days as index. Since I use the monthlocator('%m'), the x-axis is shown as number of months, as I intended.

However, there is an issue: the last tick on the x-axis is not 12 but 01. As far as I remember, some answers on similar questions mentioned that monthlocator() would locate a date to the nearest month, but this does not make sense here. The data also seems fine with dates from 2020-01-01 to 2020-12-31.

So, could anyone help point out the issue and remove that 01?

fig = plt.figure(figsize = [10, 5])
ax = fig.add_subplot(1, 1, 1)
ax.plot(df_2.loc[:, '2022'], color = 'red', linestyle = 'solid', label = '2022')
ax.plot(df_2.loc[:, '2021'], color = 'grey', linestyle = 'solid', label = '2021')
ax.plot(df_2.loc[:, '2020'], color = 'pink', linestyle = 'dashed', label = '2020')
ax.plot(df_2.loc[:, '2019'], color = 'black', linestyle = 'dashed', label = '2019')
plt.xticks(rotation='horizontal')
ax.xaxis.set_major_locator(MonthLocator())
ax.xaxis.set_major_formatter(DateFormatter('%m'))
ax.set_ylim([0, 19000])
plt.figtext(0.85, 0.825, df_type, fontsize = 'large', 
            horizontalalignment = 'right', 
            verticalalignment = 'top')
plt.figtext(0.115, 0.925, '万吨', fontsize = 'large', 
            horizontalalignment = 'right', 
            verticalalignment = 'top')
ax.legend(loc = 'best', bbox_to_anchor = (0.75, 1.095), borderpad=0.5, labelspacing=0.5, ncol = 4)

PS. Please feel free to ignore those Chinese characters. They have nothing to do with this problem.

Here is a glimpse of the data:

image

Here is the plot:

image

CodePudding user response:

You show 12 intervals (not 12 ticks) along the x-axis to represent each month of a year. Therefore you need 13 ticks to represent a year. I suppose you want to start from 0. If so then we have to use some other date formatter. For example, lambda x, pos: pos, where the pos parameter is a position of the x tick on the plot (a position for the leftmost tick is 0, the next one has a position 1 and so on), i.e. pos == x.month - 1 in this case.

The conceptual difference is that your x-axis shows the number of the current month, while this method shows the number of complete months since the beginning of the year.

Code and chart for illustration:

import matplotlib.pyplot as plt
from matplotlib.dates import MonthLocator
import pandas as pd
from  datetime import date

year_period = pd.date_range(date(2020,1,1), date(2020,12,31))
df = pd.DataFrame(index=year_period, columns=[2020])
df[2020] = year_period.month

fig = plt.figure(figsize = [10, 5])
ax = fig.add_subplot(1, 1, 1)
ax.plot(df.loc[:, '2020'], color = 'red', linestyle = 'solid', label = '2020')
plt.xticks(rotation='horizontal')
ax.set_ylim([0, 13])
ax.xaxis.set_major_locator(MonthLocator())
ax.xaxis.set_major_formatter(lambda x, pos: pos)
ax.legend()

chart

CodePudding user response:

enter image description hereI have found a solution to make everything desirable. Simply adding a line of code will remove the unnecessary final month from the x-axis and:

ax.set_xlim(np.datetime64('2020-01-01'), np.datetime64('2020-12-31'))

So far I have not got where the problem is, though I suspect that the monthlocator() locates month in a non-leap year basis, while I use the dates in 2020 to plot the x-axis. So perhaps the date Feb 29th is thought to be in March, and Dec 31st is put in Jan 2021.

  • Related