【问题标题】:how to take date value from string in python?如何从python中的字符串中获取日期值?
【发布时间】:2015-09-25 07:44:29
【问题描述】:

我正在从 URL 中获取值。

import urllib2
response = urllib2.urlopen('url')    
response.read()

它给了我太长的字符串类型输出,但我只把我有问题的地方放在这里。

字符串类型输出:

'<p>Dear Customer,</p>
<p>This notice serves as proof of delivery for the shipment listed below.</p>
<dl class="outHozFixed clearfix"><label>Weight:</label></dt><dd>18.00 lbs</dd>
<dt><label>Shipped&#047;Billed On:</label></dt><dd>09/11/2015</dd>
<dt><label>Delivered On:</label></dt><dd>09/14/2015 11:07 A.M.</dd>
<dt><label for="">Signed By:</label></dt><dd>Odedra</dd></dt>
<dt><label>Left At:</label></dt>
<dd>Office</dd></dl><p>Thank you for giving us this opportunity to serve you.</p>'

问题:

我如何获取分配给 Delivered On 的日期(09/14/2015 11:07 A.M.)?

【问题讨论】:

  • 如果时间格式有固定长度。您可能会使用类似 re.search('Delivered On:
    (.*)$',a).group(1)[:20],其中 a 是字符串
  • @Vineesh,非常感谢您的 cmets,您的代码运行良好,但在 Delivered On: 为空时失败。这是错误。 AttributeError: 'NoneType' 对象没有属性 'group'
  • 你能加一张支票吗?比如“data = re.search('Delivered On:
    (.*)$',a)”然后是“if data: data.group(1)[:20]”。这应该处理 Nonetype
  • 我添加了,但它给了我输出 this => '

标签: python string python-2.7 date python-3.x


【解决方案1】:

您可以从使用 Beautiful Soup 或其他一些 html 解析器之类的东西开始。它可能看起来像这样:

from bs4 import BeautifulSoup
import urllib2
response = urllib2.urlopen('url')    
html = response.read()
soup = BeautifulSoup(html)
datestr = soup.find("label", text="Delivered On:").find_parent("dt").find_next_sibling("dd").string

如果您需要,一旦您持有日期字符串,您可以使用strptime 将其转换为日期时间对象。

import datetime
date = datetime.datetime.strptime(datestr, "%mm/%dd/%Y %I:%M %p")

请记住 - 您通常不应该使用正则表达式解析 HTML 或 XML...

【讨论】:

  • “永不言败”。如果你想解析1B的字母,最好自己写一个解析html的工具,而不是使用BeatifulSoup,因为Soup是一个html分析的工具。它做了很多工作,你(可能)不需要。此外,Soup 的内存效率不高。
  • 哈哈好吧,是的,你是对的......永远不要说永远。我只是在想这个著名的问题(和最佳答案):stackoverflow.com/questions/1732348/…
  • 现在好多了 ;) 这是您的 +1 :) 顺便说一句,请查看该主题的第二个答案 :)
  • @Jimilian:不,正则表达式对于大量 XML 来说甚至不是一个答案。有一些快速的工具可以解析不是 BeautifulSoup 的 XML。并不意味着正则表达式是唯一的选择。
  • 一般来说,有 XML 解析器构建可用的 DOM 表示(如 BS),然后有解析器将 XML 流读入标记化流,通常仅在输入 XML 不可用时使用不适合记忆。
【解决方案2】:

试试这个代码:

import re

text = '''<p>Dear Customer,</p>
          <p>This notice serves as proof of delivery for the shipment listed below.</p>
          <dl class="outHozFixed clearfix"><label>Weight:</label></dt>
          <dd>18.00 lbs</dd>
          <dt><label>Shipped&#047;Billed On:</label></dt>
          <dd>09/11/2015</dd>
          <dt><label>Delivered On:</label></dt><dd>09/14/2015 11:07 A.M.</dd>
          <dt><label for="">Signed By:</label></dt><dd>Odedra</dd></dt>
          <dt><label>Left At:</label></dt>
          <dd>Office</dd></dl><p>Thank you for giving us this opportunity to serve you.</p>'''

re.findall(r'<dt><label>Delivered On:<\/label><\/dt><dd>([0-9\.\/\s:APM]+)', text)

输出:

['09/14/2015 11:07 A.M.']

【讨论】:

    【解决方案3】:

    仅基于该输出,我将使用rere.search。创建一个正则表达式来查找带时间的日期,如下所示:

    import re
    
    output = '''<p>Dear Customer,</p>
                <p>This notice serves as proof of delivery for the shipment listed below.</p>
                <dl class="outHozFixed clearfix"><label>Weight:</label></dt><dd>18.00 lbs</dd>
                <dt><label>Shipped&#047;Billed On:</label></dt><dd>09/11/2015</dd>
                <dt><label>Delivered On:</label></dt><dd>09/14/2015 11:07 A.M.</dd>
                <dt><label for="">Signed By:</label></dt><dd>Odedra</dd></dt>
                <dt><label>Left At:</label></dt>
                <dd>Office</dd></dl><p>Thank you for giving us this opportunity to serve you.</p>'''
    
    pattern = '\d{2}/\d{2}/\d{4} \d{1,2}:\d{2} [A|P]\.M\.'
    
    result = re.search(pattern, text, re.MULTILINE).group(0)
    

    【讨论】:

    • 非常感谢。您的代码运行良好,但在 Delivered On: 为空时失败。这是错误。 AttributeError:“NoneType”对象没有属性“组”
    【解决方案4】:

    如果你不喜欢正则表达式和第三方库,你总是可以使用老式硬编码的单行解决方案:

    import datetime
    
    text_date = [item.strip() for item in input_text.split('\n') if "Delivered On:" in item][0][41:-5]
    datetime.datetime.strptime(text_date.replace(".",""), "%m/%d/%Y %I:%M %p")
    

    单行情况:

    start_index = input_text.index("Delivered On:")+len("Delivered On:</label></dt><dd>")
    stop_index = start_index + 21
    text_date = input_text[start_index:stop_index]
    

    因为您的问题的任何解决方案都将是不同类型的硬编码:(

    【讨论】:

    • 感谢您的回答。但是这段代码不会获取日期。
    • 如果你测试@Alexandr Faizullin 代码,我得到了我想要的。但在你的情况下,我没有得到我想要的。
    • 这听起来很公平,但你得到了什么输出?你能展示一下吗?这对我来说很有趣。
    • 是的,我会的。 JFI,输入文本将在一行中,而不是 "\n" 可能会出现问题。您正在逐行测试,我在一行中得到服务器的响应。
    • @Odedra,是的,对于单行案例解决方案应该不同:)
    【解决方案5】:

    试试这个代码:

    import re
    a = """<p>Dear Customer,</p><p>This notice serves as proof of delivery for the shipment listed below.</p><dl class="outHozFixed clearfix"><label>Weight:</label></dt><dd>18.00 lbs</dd><dt><label>Shipped&#047;Billed On:</label></dt><dd>09/11/2015</dd><dt><label>Delivered On:</label></dt><dd>12/4/2015 11:07 A.M.</dd><dt><label for="">Signed By:</label></dt><dd>Odedra</dd></dt><dt><label>Left At:</label></dt><dd>Office</dd></dl><p>Thank you for giving us this opportunity to serve you.</p>"""
    data = re.search('Delivered On:</label></dt><dd>(.*)$',a)
    if data and data.group(1)[:1].isdigit(): 
        data.group(1)[:20]
    

    【讨论】:

    • 我添加了,但它给我输出 this => '
    猜你喜欢
    • 1970-01-01
    • 2017-05-07
    • 2015-05-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-05-05
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多