matplotlib绘制图上奇怪的水平线

时间:2014-02-26 17:20:33

标签: python datetime matplotlib pandas

我使用openpyxl将Excel电子表格中的数据读入一个名为“tides”的pandas数据框。该数据集包含超过32,000行数据(英国的潮汐时间每15分钟测量一次)。其中一列包含日期和时间信息(变量称为'datetime'),另一列包含潮汐的高度(称为'潮'):

我想使用以下方法绘制沿x轴的日期时间和y轴上的潮汐:

import numpy        as np
import matplotlib       as mpl
import matplotlib.pyplot    as plt
import pandas       as pd
import openpyxl
import datetime     as dt
from matplotlib.dates import date2num

<-- Data imported from Excel spreadsheet into DataFrame using openpyxl. -->
<-- Code omitted for ease of reading.                                   -->

# Convert datatime variable to datetime64 format:
tides['datetime'] = pd.to_datetime(tides['datetime'])

# Plot figure of 'datetime' vs 'tide':
fig = plt.figure()
ax_tides = fig.add_subplot(1,1,1)
ax_tides.plot_date(date2num(phj_tides['datetime']),phj_tides['tide'],'-',xdate=True,label='Tides 2011',linewidth=0.5)

min_datetime = dt.datetime.strptime('01/01/2011 00:00:00',"%d/%m/%Y %H:%M:%S")
max_datetime = dt.datetime.strptime('03/01/2011 23:59:45',"%d/%m/%Y %H:%M:%S")
ax_tides.set_xlim( [min_datetime, max_datetime] )

plt.show()

enter image description here

该图显示了数据的前几天。然而,在从一天到下一天的变化中,发生了一些奇怪的事情;在第1天的最后一个点之后,该线向右消失,然后返回以绘制第二天的第一个点 - 但数据在y轴上绘制不正确。这在整个数据集中都会发生。打印输出显示数据似乎没问题。

    number            datetime   tide
0        1 2011-01-01 00:00:00  4.296
1        2 2011-01-01 00:15:00  4.024
2        3 2011-01-01 00:30:00  3.768
3        4 2011-01-01 00:45:00  3.521
4        5 2011-01-01 01:00:00  3.292
5        6 2011-01-01 01:15:00  3.081
6        7 2011-01-01 01:30:00  2.887
7        8 2011-01-01 01:45:00  2.718
8        9 2011-01-01 02:00:00  2.577
9       10 2011-01-01 02:15:00  2.470
10      11 2011-01-01 02:30:00  2.403
11      12 2011-01-01 02:45:00  2.389
12      13 2011-01-01 03:00:00  2.417
13      14 2011-01-01 03:15:00  2.492
14      15 2011-01-01 03:30:00  2.611
15      16 2011-01-01 03:45:00  2.785
16      17 2011-01-01 04:00:00  3.020
17      18 2011-01-01 04:15:00  3.314
18      19 2011-01-01 04:30:00  3.665
19      20 2011-01-01 04:45:00  4.059
20      21 2011-01-01 05:00:00  4.483

[21 rows x 3 columns]
     number            datetime   tide
90       91 2011-01-01 22:30:00  7.329
91       92 2011-01-01 22:45:00  7.014
92       93 2011-01-01 23:00:00  6.690
93       94 2011-01-01 23:15:00  6.352
94       95 2011-01-01 23:30:00  6.016
95       96 2011-01-01 23:45:00  5.690
96       97 2011-02-01 00:00:00  5.366
97       98 2011-02-01 00:15:00  5.043
98       99 2011-02-01 00:30:00  4.729
99      100 2011-02-01 00:45:00  4.426
100     101 2011-02-01 01:00:00  4.123
101     102 2011-02-01 01:15:00  3.832
102     103 2011-02-01 01:30:00  3.562
103     104 2011-02-01 01:45:00  3.303
104     105 2011-02-01 02:00:00  3.055
105     106 2011-02-01 02:15:00  2.827
106     107 2011-02-01 02:30:00  2.620
107     108 2011-02-01 02:45:00  2.434
108     109 2011-02-01 03:00:00  2.268
109     110 2011-02-01 03:15:00  2.141
110     111 2011-02-01 03:30:00  2.060

[21 rows x 3 columns]
       number            datetime   tide
35020   35021 2011-12-31 19:00:00  5.123
35021   35022 2011-12-31 19:15:00  4.838
35022   35023 2011-12-31 19:30:00  4.551
35023   35024 2011-12-31 19:45:00  4.279
35024   35025 2011-12-31 20:00:00  4.033
35025   35026 2011-12-31 20:15:00  3.803
35026   35027 2011-12-31 20:30:00  3.617
35027   35028 2011-12-31 20:45:00  3.438
35028   35029 2011-12-31 21:00:00  3.278
35029   35030 2011-12-31 21:15:00  3.141
35030   35031 2011-12-31 21:30:00  3.019
35031   35032 2011-12-31 21:45:00  2.942
35032   35033 2011-12-31 22:00:00  2.909
35033   35034 2011-12-31 22:15:00  2.918
35034   35035 2011-12-31 22:30:00  2.923
35035   35036 2011-12-31 22:45:00  2.985
35036   35037 2011-12-31 23:00:00  3.075
35037   35038 2011-12-31 23:15:00  3.242
35038   35039 2011-12-31 23:30:00  3.442
35039   35040 2011-12-31 23:45:00  3.671

我无法解释这一点。任何人都可以解释发生了什么,为什么会发生这种情况,我该如何纠正呢?

提前致谢。

菲尔

2 个答案:

答案 0 :(得分:1)

卫生署!终于找到了答案。原来的工作流程非常复杂。我将数据存储在Excel电子表格中,并使用openpyxl从指定的单元格区域读取数据。然后将其转换为pandas DataFrame。使用pandas的.to_datetime()函数将日期和时间变量转换为日期时间格式。最后使用matplotlib绘制数据。当我准备将数据发布到这个论坛时(正如rauparaha所建议的那样)并将脚本简化为基本要素,我注意到Day1数据绘制在2011年1月1日,但Day2数据绘制在2011年2月1日。如果你看看原帖中的输出,日期是混合格式:给出的最后日期是'2011-12-31'(即年 - 月 - 日'),但代表2011年1月2日的第2个日期是'2011-02- 01'(即年 - 月 - 月)。

所以,看起来我误解了pandas .to_datetime()函数如何解释日期时间信息。我故意没有设置infer_datetime_format属性(默认= False)并假设任何问题都会被标记出来。但似乎熊猫假设日期是以月为先的格式。除非它们不是,在这种情况下,它会变为第一天的格式。我应该选择那个!

我通过提供明确定义日期时间格式的字符串来纠正问题。一切都很好。

再次感谢您的建议。并为任何困惑道歉。

干杯。

答案 1 :(得分:0)

我无法复制您的错误,但也许我的工作虚拟代码可以帮助诊断问题。我生成了虚拟数据并使用以下代码绘制它:

import pandas as pd
import numpy as np

ydata = np.sin(np.linspace(0, 10, num=200))
time_index = pd.date_range(start=pd.datetime(2000, 1, 1, 0, 0), periods=200, freq=15*pd.datetools.Minute())
df = pd.DataFrame({'tides': ydata, 'datetime': time_index})
df.plot(x='datetime', y='tides')

我的数据看起来像这样

             datetime     tides
0 2000-01-01 00:00:00  0.000000
1 2000-01-01 00:15:00  0.050230
2 2000-01-01 00:30:00  0.100333
3 2000-01-01 00:45:00  0.150183
4 2000-01-01 01:00:00  0.199654

[200 rows]

并生成以下图

enter image description here