Rolf of Saxony
Rolf of Saxony

Reputation: 22453

Find all occurrences of a variable time stamp structure in a string

Given that a time stamp can have several constructions i.e.

Currently I'm using re.findall() with the | alternates operator.

Is there a more efficient method of finding all of the above possible type of time stamps in a string than the following:

aString = "the cat  (01:03)  sat on [01:01:01] the ( 9:13 )mat( 1:10:11)."
bString = "the cat 01:14:23.447 sat on the mat"
cString = "the cat 01:14:23.447 --> 01:17:10.239 sat on the mat"
dString = "the cat 323:14 sat on the mat"


v = re.findall('\d{2}:\d{2}:\d{2}|\d:\d{2}:\d{2}|\d{3}:\d{2}|\d{2}:\d{2}|\d:\d{2}',aString)
x = re.findall('\d{2}:\d{2}:\d{2}|\d:\d{2}:\d{2}|\d{3}:\d{2}|\d{2}:\d{2}|\d:\d{2}',bString)
y = re.findall('\d{2}:\d{2}:\d{2}|\d:\d{2}:\d{2}|\d{3}:\d{2}|\d{2}:\d{2}|\d:\d{2}',cString)
z = re.findall('\d{2}:\d{2}:\d{2}|\d:\d{2}:\d{2}|\d{3}:\d{2}|\d{2}:\d{2}|\d:\d{2}',dString)

v
['01:03', '01:01:01', '9:13', '1:10:11']
x
['01:14:23']
y
['01:14:23', '01:17:10']
z
['323:14']

Note: I don't care about milliseconds if they are included in the time stamp.

Upvotes: 1

Views: 59

Answers (2)

Keyur Potdar
Keyur Potdar

Reputation: 7238

You can use this:

aString = "the cat  (01:03)  sat on [01:01:01] the ( 9:13 )mat( 1:10:11)."
bString = "the cat 01:14:23.447 sat on the mat"
cString = "the cat 01:14:23.447 --> 01:17:10.239 sat on the mat"
dString = "the cat 323:14 sat on the mat"

v = re.findall('\d{1,3}(?::\d{2}){1,2}', aString)
x = re.findall('\d{1,3}(?::\d{2}){1,2}', bString)
y = re.findall('\d{1,3}(?::\d{2}){1,2}', cString)
z = re.findall('\d{1,3}(?::\d{2}){1,2}', dString)

print(v, x, y, z, sep='\n')

Output:

['01:03', '01:01:01', '9:13', '1:10:11']
['01:14:23']
['01:14:23', '01:17:10']
['323:14']

DEMO

Explanation:

  • \d{1,3} match at least 1 and at most 3 digits
  • (?: start non-capturing group
    • :\d{2} match a colon and 2 digits
  • ) end group
  • {1,2} match the preceding group at least 1 and at most 2 times

Upvotes: 1

revo
revo

Reputation: 48741

If you're matching but not validating at the same time, below regex would be enough:

\d+:\d+(?::\d+)?

Breakdown:

  • \d+:\d+ Match a digit(s) colon digit(s) string
  • (?: Start of non-captruing group
    • :\d+ Match colon digit(s)
  • )? End of NCG, optional

Live demo

Upvotes: 1

Related Questions