熊猫在月日时间后从其余字符串中分离出来

Posted

技术标签:

【中文标题】熊猫在月日时间后从其余字符串中分离出来【英文标题】:Pandas split after month day time from rest of string 【发布时间】:2020-02-21 20:30:57 【问题描述】:

我正在使用熊猫数据框。我正在尝试从字符串的其余部分中拆分日期和时间之后的列。

df
   data
0  Oct 22 12:56:52 server1
1  Oct 22 12:56:52 server2
2  Oct 22 12:56:53 server2
3  Oct 22 12:56:54 server2
4  Oct 22 12:56:56 comp2

期望的输出:

df
   date              machine
0  Oct 22 12:56:52   server1
1  Oct 22 12:56:52   server2
2  Oct 22 12:56:53   server2
3  Oct 22 12:56:54   server2
4  Oct 22 12:56:56   comp2

如果我尝试df["data"].str.extract('^(.*? [0-9]2) (.*)$') 之类的方法,它只会在 22(天)之后删除所有内容

【问题讨论】:

【参考方案1】:

使用positive lookbehind 分割semicolontwo numbersspace

详情:

(?<=) 是积极的后视(检查字符串之前是否有任何内容) :\d2 是模式:semicolontwo numbers \s 是空格

结论:我们在whitespace 上进行拆分,但前提是它之前是上述模式。

s = df['data'].str.split('(?<=:\d2)\s')

df['date'] = s.str[0]
df['machine'] = s.str[1]
df = df.drop(columns='data')

或者作为piRSquared & jezrael suggest in the comments,单行:

df['date'], df['machine'] = zip(*df.pop('data').str.split('(?<=:\d2)\s'))

输出

              date  machine
0  Oct 22 12:56:52  server1
1  Oct 22 12:56:52  server2
2  Oct 22 12:56:53  server2
3  Oct 22 12:56:54  server2
4  Oct 22 12:56:56    comp2

【讨论】:

这里给你一些技巧(-:df['date'], df['machine'] = df.data.str.split('(?&lt;=:\d2)\s').str 另外,如果机器名总是缺少空格,那么我们可以做一个rsplit:df['date'], df['machine'] = df.data.str.rsplit(n=1).str 爱它!添加它。它如何在这里覆盖df['Data']? @piRSquared 它没有)-:你仍然需要放弃它。 嘿@jezrael 不错的一个(-:【参考方案2】:

理解

这取决于始终为 15 个字符的数据格式。 此外,由于无论如何我们都将不得不删除一列'data',我认为最好从头开始创建一个数据框。

pd.DataFrame([[s[:15], s[16:]] for s in df.data], columns=['date', 'machine'])

              date  machine
0  Oct 22 12:56:52  server1
1  Oct 22 12:56:52  server2
2  Oct 22 12:56:53  server2
3  Oct 22 12:56:54  server2
4  Oct 22 12:56:56    comp2

rsplit

取决于'machine' 名称,从不包含空格。

这是因为pandas.Series.str 提供的字符串访问器是可迭代的,可以在类似于x, y = (1, 2) 的赋值语句中使用

另外请注意,我毫无歉意地接受了使用pop in this instance from @jezrael的想法

df['date'], df['machine'] = df.pop('data').str.rsplit(n=1).str

df

              date  machine
0  Oct 22 12:56:52  server1
1  Oct 22 12:56:52  server2
2  Oct 22 12:56:53  server2
3  Oct 22 12:56:54  server2
4  Oct 22 12:56:56    comp2

【讨论】:

也许在你的答案中也添加这个:df['date'], df['machine'] = df.data.str.rsplit(n=1).str【参考方案3】:

如果格式保持不变:

df['date'] = df['data'].str[:-8]
df['machine'] = df['data'].str[-8:]

print(df)

                      data             date   machine
0  Oct 22 12:56:52 server1  Oct 22 12:56:52   server1
1  Oct 22 12:56:52 server2  Oct 22 12:56:52   server2

【讨论】:

我喜欢这个答案,但为了安全起见,我认为我们不能依赖机器名称总是 8 个字符。我认为我们最好从一开始就这样做。 df.data.str[:15]【参考方案4】:

试试这个:

r"(?<=[\S ][\d]2:[\d]2:[\d]2 )[\S ]+"

我不是最好的正则表达式,肯定有更好的方法,但这有效

【讨论】:

【参考方案5】:

您也可以传递日期\时间的确切形式:

df['data'].str.extract('(\w* \d* \d*:\d*:\d*) (.*)')

输出:

                 0        1
0  Oct 22 12:56:52  server1
1  Oct 22 12:56:52  server2
2  Oct 22 12:56:53  server2
3  Oct 22 12:56:54  server2
4  Oct 22 12:56:56    comp2

【讨论】:

df['data'].str.extract('(?P&lt;date&gt;\w* \d* \d*:\d*:\d*) (?P&lt;machine&gt;.*)')

以上是关于熊猫在月日时间后从其余字符串中分离出来的主要内容,如果未能解决你的问题,请参考以下文章

如何从查询字符串中分离“选择顶部 * x”?

如何从字符串中分离许多不同的单词(Java)

从元素中分离多行文本

如何从共享内存中分离字符串数组? C

从一个数组元素中分离两个字符串

如何在 cassandra 中将环从集群中分离出来