from string import digits def containsnumbers(value): return any(char in digits for char in value)
EDIT:
And only for thoroughness:
any (c.isdigit ()):
>>> timeit.timeit('any(c.isdigit() for c in value)', setup='value = "abcd1"') 1.4080650806427002
any (c in numbers):
>>> timeit.timeit('any(c in digits for c in value)', setup='from string import digits; value = "abcd1"') 1.392179012298584
re.search (1 or more digits):
>>> timeit.timeit("re.search('\d+', value)", setup='import re; value = "abcd1"') 1.8129329681396484
re.search (stop after one digit):
>>> timeit.timeit("re.search('\d', value)", setup='import re; value = "abcd1"') 1.599431037902832
re.match (not greedy):
>>> timeit.timeit("re.match(r'^.*?\d', value)", setup='import re; value = "abcd1"') 1.6654980182647705
re.match (greedy):
>>> timeit.timeit("re.match(r'^.*\d', value)", setup='import re; value = "abcd1"') 1.5637178421020508
any (card ()):
>>> timeit.timeit("any(map(lambda c:c.isdigit(),value))", setup='value = "abcd1"') 1.9165890216827393
any (IMAP ()):
>>> timeit.timeit("any(imap(lambda c:c.isdigit(),value))", setup='from itertools import imap;value = "abcd1"') 1.370448112487793
As a rule, less complex regular expressions ran faster. c.isdigit() and c in digits almost equivalent. re.match slightly faster than re.search . map() is the slowest solution, but imap() was the fastest (but with a rounding error of any(c.isdigit) and any(c in digits) .