Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/303.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python:使用正则表达式提取日期和时间_Python - Fatal编程技术网

Python:使用正则表达式提取日期和时间

Python:使用正则表达式提取日期和时间,python,Python,问题陈述: 我只需要在特定时间后从文件中收集日志,可以采用以下格式“Aug 7 11:00:00.000”或“Aug 7 11:00:00”。这些日志位于不同的txt文件中,其格式如下: Aug 7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K Aug 7 11:00:00.000 abc xyz lol 等等 如何使用正则表达式提取这个特定的日期和时间,然后仅在指定的时间后收集日志?除了正

问题陈述:

我只需要在特定时间后从文件中收集日志,可以采用以下格式“Aug 7 11:00:00.000”或“Aug 7 11:00:00”。这些日志位于不同的txt文件中,其格式如下:

Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K
Aug  7 11:00:00.000  abc xyz lol
等等

如何使用正则表达式提取这个特定的日期和时间,然后仅在指定的时间后收集日志?除了正则表达式,还有其他更好的使用方法吗

现在使用这个:

import re

monthnames = "(?:Jan\w*|Feb\w*|Mar\w*|Apr\w*|May|Jun\w?|Jul\w?|Aug\w*|Sep\w*|Oct\w*|Nov(?:ember)?|Dec\w*)"

pattern1 = re.compile(r"(\d{1,4}[\/\\\-]+\d{1,2}[\/\\\-]+\d{2,4})")

pattern4 = re.compile(r"(?:[\d,. \-]*[,. \-])?%s(?:[\,\.\ \-]+[\d]+[stndrh]*)+[:\d]*[\ ]?(PM)?(AM)?([\ \-\+\d]{4,7}|[UTCESTGMT\ ]{2,4})*"%monthnames, re.I)

patterns = [pattern4, pattern1]

s='Aug 7 11:00:00.000'

for pattern in patterns:
    print re.findall(pattern,s)
但它什么也不返回,一个空列表

需要帮助


注-我只能使用python中的传统库,因为这是一个用于Junos的自动化脚本

你肯定不需要正则表达式来实现这一点-在空白处简单拆分并收集前两个结果就足够了,即:

log_lines = ["Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K",
             "Aug  7 11:00:00.000  abc xyz lol"]  # we'll use a list as an example

for line in log_lines:
    date_string = " ".join(line.split(None, 3)[:-1])
    print(date_string)

# Aug 7 11:00:00
# Aug 7 11:00:00.000
现在,您可以使用将其解析为本机日期时间对象,但您可能会受到格式限制(即,
%b
仅是当前区域设置的月份缩写,并非所有平台/版本都支持单位数日期),因此,鉴于这种简单的结构,您可能希望在解析捕获的日期-时间字符串之前重新生成它们,以最大限度地提高兼容性:

month_abbr = {"jan": 1, "feb": 2, "mar": 3, "apr": 4, "may": 5, "jun": 6,
              "jul": 7, "aug": 8, "sep": 9, "oct": 10, "nov": 11, "dec": 12}

def parse_date(log_line):
    mon, day, tim = line.split(None, 3)[:-1]
    date_string = "{:02} {:02} ".format(month_abbr[mon.lower()], int(day)) + tim
    try:
        return datetime.datetime.strptime(date_string, "%m %d %H:%M:%S.%f")
    except ValueError as e:
        return datetime.datetime.strptime(date_string, "%m %d %H:%M:%S")

log_lines = ["Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K",
             "Aug  7 11:00:00.000  abc xyz lol"]  # we'll use a list as an example

for line in log_lines:
    date_object = parse_date(line)
    print(date_object)

# 1900-08-07 11:00:00
# 1900-08-07 11:00:00
注意:日期时间对象的年份为
1900
,因为日志中没有年份信息。第二个日期时间对象也包含它的微秒数据,它只是不以对象的默认表示形式打印出来

现在,您可以将这些日期时间对象与其他日期时间对象进行比较,并过滤/打印/执行与您的条件匹配的任何操作,例如,如果您只希望在8月7日之后创建日志,请执行以下操作:

log_lines = ["Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K",
             "Aug  7 11:00:00.000  abc xyz lol",
             "Aug  8 11:00:00 foo bar"]  # we'll use a list as an example

min_date = datetime.datetime(1900, 8, 8)  # minimum date set to Aug 8

for line in log_lines:
    if parse_date(line) >= min_date:
        print(line)

# Aug  8 11:00:00 foo bar

您肯定不需要正则表达式来完成此操作-在空白处进行简单拆分并收集前两个结果就足够了,即:

log_lines = ["Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K",
             "Aug  7 11:00:00.000  abc xyz lol"]  # we'll use a list as an example

for line in log_lines:
    date_string = " ".join(line.split(None, 3)[:-1])
    print(date_string)

# Aug 7 11:00:00
# Aug 7 11:00:00.000
现在,您可以使用将其解析为本机日期时间对象,但您可能会受到格式限制(即,
%b
仅是当前区域设置的月份缩写,并非所有平台/版本都支持单位数日期),因此,鉴于这种简单的结构,您可能希望在解析捕获的日期-时间字符串之前重新生成它们,以最大限度地提高兼容性:

month_abbr = {"jan": 1, "feb": 2, "mar": 3, "apr": 4, "may": 5, "jun": 6,
              "jul": 7, "aug": 8, "sep": 9, "oct": 10, "nov": 11, "dec": 12}

def parse_date(log_line):
    mon, day, tim = line.split(None, 3)[:-1]
    date_string = "{:02} {:02} ".format(month_abbr[mon.lower()], int(day)) + tim
    try:
        return datetime.datetime.strptime(date_string, "%m %d %H:%M:%S.%f")
    except ValueError as e:
        return datetime.datetime.strptime(date_string, "%m %d %H:%M:%S")

log_lines = ["Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K",
             "Aug  7 11:00:00.000  abc xyz lol"]  # we'll use a list as an example

for line in log_lines:
    date_object = parse_date(line)
    print(date_object)

# 1900-08-07 11:00:00
# 1900-08-07 11:00:00
注意:日期时间对象的年份为
1900
,因为日志中没有年份信息。第二个日期时间对象也包含它的微秒数据,它只是不以对象的默认表示形式打印出来

现在,您可以将这些日期时间对象与其他日期时间对象进行比较,并过滤/打印/执行与您的条件匹配的任何操作,例如,如果您只希望在8月7日之后创建日志,请执行以下操作:

log_lines = ["Aug  7 11:00:00 abc newsyslog[25714]: logfile turned over due to size>1024K",
             "Aug  7 11:00:00.000  abc xyz lol",
             "Aug  8 11:00:00 foo bar"]  # we'll use a list as an example

min_date = datetime.datetime(1900, 8, 8)  # minimum date set to Aug 8

for line in log_lines:
    if parse_date(line) >= min_date:
        print(line)

# Aug  8 11:00:00 foo bar

我认为regex在这方面做得太过分了,我会提取日期部分,比如:

' '.join(line.split()[0:3])
并与较长的格式一起使用,捕获异常,然后尝试使用strtime以获得较短的格式:

from datetime import datetime

def get_date(date_str):
    try:
        return datetime.strptime(date_str, '%b %d %H:%M:%S.%f')
    except ValueError:
        return datetime.strptime(date_str, '%b %d %H:%M:%S')

我认为regex在这方面做得太过分了,我会提取日期部分,比如:

' '.join(line.split()[0:3])
并与较长的格式一起使用,捕获异常,然后尝试使用strtime以获得较短的格式:

from datetime import datetime

def get_date(date_str):
    try:
        return datetime.strptime(date_str, '%b %d %H:%M:%S.%f')
    except ValueError:
        return datetime.strptime(date_str, '%b %d %H:%M:%S')

为什么不使用内置的
datetime
模块的
strtime
功能?您能举个例子吗?
datetime.strtime('2018年8月13日星期一','%a,%B%d,%Y')
返回对应于2018年8月13日的
datetime
对象。您可以通过阅读了解更多信息。为什么不使用内置的
datetime
模块的
strtime
功能?您能举个例子吗?
datetime.strtime('2018年8月13日星期一,'%a,%B%d,%Y')
返回对应于2018年8月13日的
datetime
对象。您可以通过阅读了解更多。提取时间后,我只需要提取在指定时间后收集的日志,例如提取8月6日12:45:30.650,假设日期和时间解析为8月6日13:45:50.123。我只需要在此指定时间之后提取日志。我该怎么做?现在困了很长时间了!我需要使用日期和时间作为参数来收集日志,这只是比较date@P.Saini-
datetime.datetime也包含一个时间组件。例如,如果要将最短日期设置为8月8日上午8:30,可以使用:
min\u date=datetime.datetime(1900,8,8,8,30)
。定义签名时,请检查签名以查看所有可用组件。提取时间后,我只需要提取在指定时间后收集的日志,如提取8月6日12:45:30.650,假设日期和时间解析为8月6日13:45:50.123。我只需要在此指定时间之后提取日志。我该怎么做?现在困了很长时间了!我需要使用日期和时间作为参数来收集日志,这只是比较date@P.Saini-
datetime.datetime也包含一个时间组件。例如,如果要将最短日期设置为8月8日上午8:30,可以使用:
min\u date=datetime.datetime(1900,8,8,8,30)
。在定义签名时,请检查签名以查看所有可用组件。