如何平滑 matplotlib 中的折线图?
How can I smoothen a line chart in matplotlib?
我已经尝试了所有方法并查看了这里的其他线程,但我找不到如何平滑 matplotlib 图表中的线条。问题是,在大多数教程中,两个轴都有数值,而在我的例子中,对于我的 x 轴,我有一个日期值...
这可能吗?如果没有,是否有任何其他可视化库可以让我这样做?
这是我的代码:
date = ["Jan", "Feb", "Mar", "Apr", "May"]
value = [4,12,15,7,25]
plt.plot(date,value)
plt.show()
当前输出的是:
我想这样显示:
非常感谢!
我撤回了我的接近投票,因为我错过了你在 x 轴上针对字符串绘制的问题(因此在它们之间进行插值更加困难)。正如其他人所建议的那样,关键是使用您的日期字符串来获取用于绘图和插值的数字。一旦你这样做了,this answer 仍然是一个很好的框架。
import matplotlib.pyplot as plt
import numpy as np
from scipy.interpolate import make_interp_spline
# original data
date = ["Jan", "Feb", "Mar", "Apr", "May"]
value = [4,12,15,7,25]
# create integers from strings
idx = range(len(date))
xnew = np.linspace(min(idx), max(idx), 300)
# interpolation
spl = make_interp_spline(idx, value, k=3)
smooth = spl(xnew)
# plotting, and tick replacement
plt.plot(xnew, smooth)
plt.xticks(idx, date)
idx
是值(0, 1, 2, 3, 4)
,用于绘图和插值。最后,对 xticks
的调用用于使用日期字符串来标记那些刻度位置。
以上内容主要基于评论(来自HenryEcker and JohanC)。我想添加的新内容是另一种进行插值的方法是将字符串转换为实际的日期时间:
import matplotlib.dates as mdates # for formatting
import matplotlib.pyplot as plt
from scipy.interpolate import make_interp_spline
import pandas as pd # for working with dates
# instead of ["Jan", "Feb", "Mar", "Apr", "May"], create datetime objects
date = pd.date_range('01-01-2020', freq='MS', periods=5)
# DatetimeIndex(['2020-01-01', '2020-02-01', '2020-03-01', '2020-04-01', '2020-05-01'], dtype='datetime64[ns]', freq='MS')
value = [4,12,15,7,25]
# now make new x positions using a date range, instead of linspace
# see here:
xnew = pd.date_range(date.min(), date.max(), periods=300)
# interpolation
spl = make_interp_spline(date, value, k=3)
smooth = spl(xnew)
# plotting
plt.plot(xnew, smooth)
# using mdates to get the x-axis formatted correctly
months = mdates.MonthLocator()
fmt = mdates.DateFormatter('%b') # %b -> Month as locale’s abbreviated name
ax = plt.gca()
ax.xaxis.set_major_locator(months)
ax.xaxis.set_major_formatter(fmt)
后一种方法涉及一些额外的格式化工作(和导入),但它在绘制时态数据方面更加明确。我发现这可以更直观地使用。例如,如果您有多个时间序列,您可以轻松地将它们并排绘制;您可以在代码中更轻松地引用特定日期;您不必记住哪些索引指的是哪些日期(例如本例中的三月和 2
)等...
我已经尝试了所有方法并查看了这里的其他线程,但我找不到如何平滑 matplotlib 图表中的线条。问题是,在大多数教程中,两个轴都有数值,而在我的例子中,对于我的 x 轴,我有一个日期值...
这可能吗?如果没有,是否有任何其他可视化库可以让我这样做?
这是我的代码:
date = ["Jan", "Feb", "Mar", "Apr", "May"]
value = [4,12,15,7,25]
plt.plot(date,value)
plt.show()
当前输出的是:
我想这样显示:
非常感谢!
我撤回了我的接近投票,因为我错过了你在 x 轴上针对字符串绘制的问题(因此在它们之间进行插值更加困难)。正如其他人所建议的那样,关键是使用您的日期字符串来获取用于绘图和插值的数字。一旦你这样做了,this answer 仍然是一个很好的框架。
import matplotlib.pyplot as plt
import numpy as np
from scipy.interpolate import make_interp_spline
# original data
date = ["Jan", "Feb", "Mar", "Apr", "May"]
value = [4,12,15,7,25]
# create integers from strings
idx = range(len(date))
xnew = np.linspace(min(idx), max(idx), 300)
# interpolation
spl = make_interp_spline(idx, value, k=3)
smooth = spl(xnew)
# plotting, and tick replacement
plt.plot(xnew, smooth)
plt.xticks(idx, date)
idx
是值(0, 1, 2, 3, 4)
,用于绘图和插值。最后,对 xticks
的调用用于使用日期字符串来标记那些刻度位置。
以上内容主要基于评论(来自HenryEcker and JohanC)。我想添加的新内容是另一种进行插值的方法是将字符串转换为实际的日期时间:
import matplotlib.dates as mdates # for formatting
import matplotlib.pyplot as plt
from scipy.interpolate import make_interp_spline
import pandas as pd # for working with dates
# instead of ["Jan", "Feb", "Mar", "Apr", "May"], create datetime objects
date = pd.date_range('01-01-2020', freq='MS', periods=5)
# DatetimeIndex(['2020-01-01', '2020-02-01', '2020-03-01', '2020-04-01', '2020-05-01'], dtype='datetime64[ns]', freq='MS')
value = [4,12,15,7,25]
# now make new x positions using a date range, instead of linspace
# see here:
xnew = pd.date_range(date.min(), date.max(), periods=300)
# interpolation
spl = make_interp_spline(date, value, k=3)
smooth = spl(xnew)
# plotting
plt.plot(xnew, smooth)
# using mdates to get the x-axis formatted correctly
months = mdates.MonthLocator()
fmt = mdates.DateFormatter('%b') # %b -> Month as locale’s abbreviated name
ax = plt.gca()
ax.xaxis.set_major_locator(months)
ax.xaxis.set_major_formatter(fmt)
后一种方法涉及一些额外的格式化工作(和导入),但它在绘制时态数据方面更加明确。我发现这可以更直观地使用。例如,如果您有多个时间序列,您可以轻松地将它们并排绘制;您可以在代码中更轻松地引用特定日期;您不必记住哪些索引指的是哪些日期(例如本例中的三月和 2
)等...