【问题标题】:Regex to match mm/dd/yyyy hh:mm:ss AM or PM正则表达式匹配 mm/dd/yyyy hh:mm:ss AM 或 PM
【发布时间】:2016-11-04 05:25:34
【问题描述】:

我有一个创建时间戳信息的程序,时间戳必须符合以下格式:MM/DD/YYYY HH:MM:SS AM or PM

例如:

06/02/2016 10:14:56 AM

09/14/2014 9:16:32 PM

我需要一种使用正则表达式匹配此信息的方法,但它不必是正则表达式。对此的任何帮助将不胜感激。

我知道如何匹配数字 /\d+/ 和非空白字符,但是匹配数字不会抓取 :/AM or PM。并且抓取非空白将抓取除明显空白之外的所有内容。

所以回顾一下,我需要一种方法来验证格式化的时间和日期:MM/DD/YYYY HH:MM:SS AM or PM 它可以包含 20 到 22 个字符(包括空格),或者没有作为用户输入给出。

我需要的示例:

def timestamp
  print 'Enter the time stamp to verify: '
  ts = gets.chomp
  if !(ts[REGEX-HERE])
    puts 'Invalid formatting of time stamp'
    exit 1
  else
    puts ts
  end
end

# <= 6/1/2016 1:10:5 PM will output '6/1/2016 1:10:5 PM'
# <= 06/01/2016 01:10:05 PM will output 'Invalid formatting of time stamp'
# <= 10/1/2016 1:25:43 AM will output '10/1/2016 1:25:43 AM'
# <= 10/01/2016 01:25:43 AM will output 'Invalid formatting of time stamp'

【问题讨论】:

  • 我明白了。您想匹配 09/14/2014 9:16:32 PM 或 09/14/2014 9:16:32 AM
  • 我想匹配一个可以包含 16 到 20 个字符(包括空格)的格式化时间戳 这些时间戳的示例是 10/22/2016 9:15:32 PM9/9/2016 9:9:5 PM 他们没有12点以下时,他们前面的数字0
  • 您需要展示您生成正则表达式的尝试,而不是要求我们为您编写。正则表达式有很好的文档记录,包括在 Ruby 的 Regexp 类中,因此编写模式应该很容易研究和弄清楚。 meta.stackoverflow.com/q/261592/128421

标签: ruby regex date time format


【解决方案1】:

这个正则表达式应该适合您验证您的输入:

^\d{1,2}\/\d{1,2}\/\d{4} \d{1,2}:\d{1,2}:\d{1,2} [AP]M\z

RegEx Demo

这将验证以下任一输入行:

10/22/2016 9:15:32 PM
9/9/2016 9:9:5 AM

【讨论】:

  • 它还将验证str = "99/99/9999 9:99:99 PM": str =~ /^\d{1,2}\/\d{1,2}\/\d{4} \d{1,2}:\d{1,2}:\d{1,2} [AP]M\z/ #=&gt; 0
  • Right Cary,这个正则表达式仅用于验证格式。对于实际的日期解析正则表达式可能非常讨厌,最好使用strptime
  • 注意 Ruby 中的 ^$,它们指的是 line 而不是 string。而且您的 Rubular 示例与您的答案不符。
  • 我在演示中使用^\d{1,2}\/\d{1,2}\/\d{4} \d{1,2}:\d{1,2}:\d{1,2} [AP]M$ 来显示多行匹配。 OP肯定可以使用^\A{1,2}\/\d{1,2}\/\d{4} \d{1,2}:\d{1,2}:\d{1,2} [AP]M\z
【解决方案2】:

我不认为正则表达式是适合这项工作的工具。我会使用DateTime.strptime,给它你期望的格式,让它处理所有“50 小时在一天中的某个时间是无效的”、“09 对 9”,......问题。

类似:

require 'date'

def timestamp
  print 'Enter the time stamp to verify: '
  ts = gets.chomp # You might want to include a String#strip call in here too
  DateTime.strptime(ts, '%m/%d/%Y %I:%M:%S %p')
  puts ts
rescue ArgumentError
  puts 'Invalid formatting of time stamp'
  exit 1
end

正则表达式很好,但它们不应该是您拥有的唯一解析工具。

【讨论】:

    【解决方案3】:

    /: 等字符,甚至可以随意添加字母。试试这个:

    /[01][0-9]/[0-3][0-9]/[0-9]{4} [0-2]?[0-9]:[0-6]?[0-9]:[0-6]?[0-9] (AM|PM)/
    

    【讨论】:

      【解决方案4】:

      试试这个。我希望我理解你的问题。在这里测试http://rubular.com/ 并且它有效。

        ^(\d{1,2}\/){2}\d{4}\s+((\d+)(\:)){2}\d+\s+(AM|PM)
      

      【讨论】:

        【解决方案5】:

        就像mu is too short 所说的那样,正则表达式很棒,但你需要更多的东西在你的武器库中。

        def timestamp
          print 'Enter time stamp: '
          ts = gets.chomp.upcase
          verify = DateTime.strptime(ts, '%m/%d/%Y %I:%M:%S %p')
          puts ts
        rescue ArgumentError
          puts 'Invalid timestamp formatting must contain date time AM or PM'
          timestamp
        end
        

        当然这可能会导致缓冲区溢出,因为它是递归的,但发生这种情况的可能性很小。

        运行时:

        irb(main):01:0> def timestamp
        irb(main):02:1>   print 'Enter time stamp: '
        irb(main):02:1>   ts = gets.chomp.upcase
        irb(main):04:1>   verify = DateTime.strptime(ts, '%m/%d/%Y %I:%M:%S %p')
        irb(main):05:1>   puts ts
        irb(main):06:1> rescue ArgumentError
        <valid timestamp formatting must contain date time AM or PM'
        irb(main):07:1>   timestamp
        irb(main):08:1> end
        => :timestamp
        irb(main):09:0> timestamp
        Enter time stamp: test
        Invalid timestamp formatting must contain date time AM or PM
        Enter time stamp: 06/30/2016 6:6:54 pm
        06/30/2016 6:6:54 PM
        => nil
        

        但是,您可以采用更好的检查方式:

        def enter_stamp
          print 'Enter timestamp: '
          ts = gets.chomp
          verify_stamp(ts)
        end
        
        def verify_stamp(timestamp)
          Date.strptime(timestamp, '%m/%d/%Y %I:%M:%S %p')
          puts timestamp unless ArgumentError
        rescue ArgumentError
          puts 'Invalid timestamp format'
          enter_stamp
        end
        

        这使得方法更加面向 OOP,而 Ruby 完全是面向 OOP 的,所以它有点工作。运行时:

        irb(main):001:0> require 'date'
        => true
        irb(main):002:0>
        irb(main):003:0* def enter_stamp
        irb(main):004:1>   print 'Enter timestamp: '
        irb(main):005:1>   ts = gets.chomp
        irb(main):006:1>   verify_stamp(ts)
        irb(main):007:1> end
        => :enter_stamp
        irb(main):008:0>
        irb(main):009:0* def verify_stamp(timestamp)
        irb(main):010:1>   Date.strptime(timestamp, '%m/%d/%Y %I:%M:%S %p')
        irb(main):011:1>   puts timestamp unless ArgumentError
        irb(main):012:1> rescue ArgumentError
        irb(main):013:1>   puts 'Invalid timestamp format'
        irb(main):014:1>   enter_stamp
        irb(main):015:1> end
        => :verify_stamp
        irb(main):016:0> enter_stamp
        Enter timestamp: test
        Invalid timestamp format
        Enter timestamp: 06/12/2016 8:08:54 pm
        => nil
        

        当然你也可以只使用一个正则表达式:

        def verify_timestamp(stamp)
          if !(stamp[/^\d{1,2}\/\d{1,2}\/\d{4} \d{1,2}:\d{1,2}:\d{1,2} [AP]M\z/])
            puts 'Invalid timestamp formatting'
            timestamp
          else
            stamp
          end
        end
        
        def timestamp
          print 'Enter timestamp for removal: '
          ts = gets.chomp
          verify_timestamp(ts)
        end
        

        正如我所说的正则表达式很棒,但它们并不是一直都是最好的。当运行时:

        irb(main):001:0> def verify_timestamp(stamp)
        <mp[/^\d{1,2}\/\d{1,2}\/\d{4} \d{1,2}:\d{1,2}:\d{1,2} [AP]M\z/])
        irb(main):003:2>     puts 'Invalid timestamp formatting'
        irb(main):004:2>     timestamp
        irb(main):005:2>   else
        irb(main):006:2*     stamp
        irb(main):007:2>   end
        irb(main):008:1> end
        => :verify_timestamp
        irb(main):009:0>
        irb(main):010:0* def timestamp
        irb(main):011:1>   print 'Enter timestamp for removal: '
        irb(main):012:1>   ts = gets.chomp
        irb(main):013:1>   verify_timestamp(ts)
        irb(main):014:1> end
        => :timestamp
        irb(main):015:0> verify_timestamp(timestamp)
        Enter timestamp for removal: test
        Invalid timestamp formatting
        Enter timestamp for removal: 06/12/2016 8:18:54 pm
        => "06/12/2016 8:18:54 pm"
        irb(main):016:0>
        

        所以你有它,有三种不同的方法来验证你的时间戳,这取决于你想用它们做什么可能是另一回事,但这三种方法中的任何一种都可以解决问题。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2015-01-25
          • 1970-01-01
          • 1970-01-01
          • 2019-04-03
          • 2017-04-08
          • 2017-07-10
          • 2014-02-06
          相关资源
          最近更新 更多