Python 在pyplot测线图中放置间隙/断点而不丢失数据

Python 在pyplot测线图中放置间隙/断点而不丢失数据,python,numpy,matplotlib,Python,Numpy,Matplotlib,我有一个时间序列,有几个大的数据缺口。我希望在相隔不到一小时的数据点之间看到一条连接线,但如果差距更大,则不希望看到。对这个问题的公认答案,除了你牺牲蒙面分数外,是有效的。我想避免这种情况 我曾尝试创建一个列表,将NaN插入数组,我认为这将自动实现相同的结果,但我似乎无法正确执行。我发现最好的是: import datetime as dtm import numpy as np x = np.array([dtm.datetime(2001,4,3,0,47,30),dtm.datet

我有一个时间序列,有几个大的数据缺口。我希望在相隔不到一小时的数据点之间看到一条连接线,但如果差距更大,则不希望看到。对这个问题的公认答案,除了你牺牲蒙面分数外,是有效的。我想避免这种情况

我曾尝试创建一个列表,将NaN插入数组,我认为这将自动实现相同的结果,但我似乎无法正确执行。我发现最好的是:

import datetime as dtm
import numpy    as np

x = np.array([dtm.datetime(2001,4,3,0,47,30),dtm.datetime(2001,4,3,0,52,30),dtm.datetime(2001,4,3,0,57,30),dtm.datetime(2001,4,3,3,57,30),dtm.datetime(2001,4,3,4,2,30),dtm.datetime(2001,4,3,4,7,30)])

xmod = np.array([x[0]]+[dt1 if dt1-dt0 < dtm.timedelta(hours=1.) else [dt1,np.nan] for dt1, dt0 in zip(x[1:],x[:-1])])

我无法找到一种方法来插入数据点和np.nan,而不在它们周围加上括号。这可能吗?有没有更好的方法来实现我的目标?谢谢

根据上面的评论,最简单的方法可能是将数据分成需要间隙的组。这里有一种方法可以实现这一点

import datetime as dtm
import numpy as np
import matplotlib.pyplot as plt
import pandas as pd

x = np.array([dtm.datetime(2001,4,3,0,47,30),dtm.datetime(2001,4,3,0,52,30),dtm.datetime(2001,4,3,0,57,30),
              dtm.datetime(2001,4,3,3,57,30),dtm.datetime(2001,4,3,4,2,30),dtm.datetime(2001,4,3,4,7,30)])

y = range(len(x))

# make a dataframe with groups separated that are over an hour apart
data = []
g = 0
for i in range(len(x)):
    x0 = x[i]
    y0 = y[i]
    if i < (len(x)-1):
        x1 = x[i+1]
        td = x1 - x0
        elapsed_seconds = td.total_seconds()
        hrs = (elapsed_seconds/60)/60
        if hrs < 1:
            data.append([x0,y0, g])
        else:
            data.append([x0,y0, g])
            g+=1
    else:
        data.append([x0,y0, g])

df = pd.DataFrame(data, columns=['x', 'y', 'group'])

# draw a plot
fig, ax = plt.subplots(1,1, figsize = (8,5))
for i, dfg in df.groupby('group'):

    ax.plot(dfg['x'], dfg['y'], c='b')
将日期时间导入为dtm
将numpy作为np导入
将matplotlib.pyplot作为plt导入
作为pd进口熊猫
x=np.数组([dtm.datetime(2001,4,3,0,47,30),dtm.datetime(2001,4,3,0,52,30),dtm.datetime(2001,4,3,0,57,30),
dtm.datetime(2001,4,3,3,57,30),dtm.datetime(2001,4,3,4,2,30),dtm.datetime(2001,4,3,4,7,30)])
y=范围(len(x))
#制作一个数据帧,分组间隔超过一小时
数据=[]
g=0
对于范围内的i(len(x)):
x0=x[i]
y0=y[i]
如果i<(len(x)-1):
x1=x[i+1]
td=x1-x0
已用秒数=总秒数()
小时=(已用秒/60)/60
如果hrs<1:
data.append([x0,y0,g])
其他:
data.append([x0,y0,g])
g+=1
其他:
data.append([x0,y0,g])
df=pd.DataFrame(数据,列=['x','y','group'])
#绘图
图,ax=plt.子批次(1,1,figsize=(8,5))
对于i,df.groupby('group')中的dfg:
ax.plot(dfg['x'],dfg['y'],c='b')

因此,我接受了djakubosky的答案,因为它看起来很干净,可能是正确的方法。然而,当答案发布时,我已经决定我所做的不适合列表理解,而只是将其作为for循环来写——这很好。这可能对其他人有用。代码如下:

def insert_breaks(x,y):
    import datetime as dtm
    import numpy    as np

    xnew = []
    ynew = []
    for dt1, dt0, y1, y0 in zip(x[1:],x[:-1],y[1:],y[:-1]):
        if dt1-dt0 < dtm.timedelta(hours=1):
            xnew+=[dt0]
            ynew+=[y0]
        else:
            xnew+=[dt0,dt0+(dt1-dt0)/2]
            ynew+=[y0, np.nan]

    xnew+=[dt1]
    ynew+=[y1]

    return xnew, ynew
def插入中断(x,y):
将日期时间导入为dtm
将numpy作为np导入
xnew=[]
ynew=[]
对于zip中的dt1、dt0、y1、y0(x[1:],x[:-1],y[1:],y[:-1]):
如果dt1-dt0
如何将数据集拆分为一系列子集?您将能够单独绘制每个集合,并且间隙将自然出现。你只需要找到一种合适的分割方法(当数据点相隔超过1小时时)。@taras我认为你的方法可能是合适的方法。列表理解可能并不打算一次添加两个连续的元素。
def insert_breaks(x,y):
    import datetime as dtm
    import numpy    as np

    xnew = []
    ynew = []
    for dt1, dt0, y1, y0 in zip(x[1:],x[:-1],y[1:],y[:-1]):
        if dt1-dt0 < dtm.timedelta(hours=1):
            xnew+=[dt0]
            ynew+=[y0]
        else:
            xnew+=[dt0,dt0+(dt1-dt0)/2]
            ynew+=[y0, np.nan]

    xnew+=[dt1]
    ynew+=[y1]

    return xnew, ynew