Газу з ліку з радка

У нас ёсць куча радкоў, напрыклад: c1309 , IF1306 , v1309 , p1209 , a1309 , mo1309 .
У Python, што гэта лепшы спосаб, каб вычысціць нумары? Усё, што мне трэба: з , IF , v , р , а , мо зверху, напрыклад.

16
дададзена аўтар jamylak, крыніца
@HamZa Простыя пытанні, хутчэй за ўсё, будзе upvoted, таму што яны могуць быць лёгка і хутка выконвацца ўсімі карыстальнікамі, у тым ліку тых, хто нават не знаёмы з мовай.
дададзена аўтар jamylak, крыніца
@jamylak Хахаха навучуся пітона!
дададзена аўтар HamZa, крыніца
@jamylak досыць сумна, трохі раўнуе, калі шчыра ...
дададзена аўтар HamZa, крыніца
Чаму гэты просты пытанне upvoted так о_О? Акрамя таго, можна проста шукаць і выкарыстоўваць "зваротная" рашэнне гэтай адзін .
дададзена аўтар HamZa, крыніца
@HamZa гэта праблема фар ровара.
дададзена аўтар MikeTheLiar, крыніца

8 адказы

Вы можаце выкарыстоўваць рэгулярны выраз :

>>> import re
>>> strs = "c1309, IF1306, v1309, p1209, a1309, mo1309"
>>> re.sub(r'\d','',strs)
'c, IF, v, p, a, mo'

або больш хуткі варыянт:

>>> re.sub(r'\d+','',strs)
'c, IF, v, p, a, mo'

timeit comparisons:

>>> strs = "c1309, IF1306, v1309, p1209, a1309, mo1309"*10**5

>>> %timeit re.sub(r'\d','',strs)
1 loops, best of 3: 1.23 s per loop

>>> %timeit re.sub(r'\d+','',strs)
1 loops, best of 3: 480 ms per loop

>>> %timeit ''.join([c for c in strs if not c.isdigit()])
1 loops, best of 3: 1.07 s per loop

#winner
>>> %timeit from string import digits;strs.translate(None, digits)
10 loops, best of 3: 20.4 ms per loop
27
дададзена
@GrijeshChauhan: Напэўна, няма або, па меншай меры, не істотна, калі вы не кампіляваць рэгулярны выраз, выкарыстоўваючы re.UNICODE .
дададзена аўтар Tim Pietzcker, крыніца
Лепш выкарыстоўваць re.sub (г '\ D +', '', СПО) , хоць, для павышэння эфектыўнасці.
дададзена аўтар Tim Pietzcker, крыніца
@TimPietzcker Калі нумар толькі дзесятковы той жа re.sub (г '[0-9] +', '', СПО) палепшыць хуткасць <�б> ??
дададзена аўтар Grijesh Chauhan, крыніца
@TimPietzcker дзякуй, не ведаў пра гэта.
дададзена аўтар Ashwini Chaudhary, крыніца
Вялікі дзякуй Ashwini
дададзена аўтар Can Lu, крыніца
>>> text = 'mo1309'
>>> ''.join([c for c in text if not c.isdigit()])
'mo'

Гэта хутчэй, чым рэгулярны выраз

python -m timeit -s "import re; text = 'mo1309'" "re.sub(r'\d','',text)"
100000 loops, best of 3: 3.99 usec per loop
python -m timeit -s "import re; text = 'mo1309'" "''.join([c for c in text if not c.isdigit()])"
1000000 loops, best of 3: 1.42 usec per loop
python -m timeit -s "from string import digits; text = 'mo1309'" "text.translate(None, digits)"
1000000 loops, best of 3: 0.42 usec per loop

але str.translate як прапанавана @DavidSousa :

from string import digits
text.translate(None, digits)

заўсёды самы хуткі ў зачысткі знакаў.

Also itertools supplies a little known function called ifilterfalse

>>> from itertools import ifilterfalse
>>> ''.join(ifilterfalse(str.isdigit, text))
'mo'
21
дададзена
Ці з'яўляецца далучыцца да са спісам разумення хутчэй, чым далучыцца да з выразам генератара?
дададзена аўтар Blender, крыніца
дададзена аўтар Ashwini Chaudhary, крыніца
Для вялікіх радкоў яны амаль эквівалентныя.
дададзена аўтар Ashwini Chaudhary, крыніца

Я думаю, што метад радок пераклад элегантней, чым далучэнне спісы і г.д.

from string import digits # digits = '0123456789'
list1 = ['c1309', 'IF1306', 'v1309', 'p1209', 'a1309', 'mo1309']
list2 = [ i.translate(None, digits) for i in list1 ]
13
дададзена
@jamylak я змяніў яго толькі, каб выглядаць больш ясна.
дададзена аўтар David Sousa, крыніца
<�Код> з радка імпарту лічбаў быў лепш (не ведаю, чаму вы змянілі яго). Гэта самы хуткі спосаб, і можа быць, магчыма, больш вытанчаным ў Python 2, але ў Python 3 выглядае наступным чынам: text.translate (str.maketrans ( «», «», лічбы))
дададзена аўтар jamylak, крыніца
+1, але вы можаце выкарыстоўваць спіс разуменне, каб зрабіць яго яшчэ больш элегантным.
дададзена аўтар Jan Wrobel, крыніца

Я думаю, што гэта самае простае, і, верагодна, будзе самым хуткім таксама.

>>> import string
>>> s = 'c1309, IF1306, v1309, p1209, a1309, mo1309'
>>> s.translate(None, string.digits)
'c, IF, v, p, a, mo'

Заўвага: інтэрфейс str.translate быў зменены, каб выкарыстоўваць адлюстраванне ў Python3, так вось 3 версія

s.translate({ord(n): None for n in string.digits})

Ці больш відавочная альтэрнатыва:

m = str.maketrans('', '', string.digits)
s.translate(m)
3
дададзена

If all the strings you are dealing with end with a number you can, literally, strip the number:

>>> strings = ['c1309', 'IF1306', 'v1309', 'p1209', 'a1309', 'mo1309']
>>> [s.strip("0123456789") for s in strings]
['c', 'IF', 'v', 'p', 'a', 'mo']

Калі вы хочаце, каб выдаліць лічбы толькі у канцы выкарыстання радкі rstrip . Калі лічбы могуць з'явіцца ўнутры радка, то гэты метад не будзе працаваць наогул.

1
дададзена
+1. Гэта, верагодна, усё, што патрэбы ОП. Можна таксама замяніць 0123456789 у растворы з string.digits
дададзена аўтар iruvar, крыніца
strings = ['c1309', 'IF1306', 'v1309', 'p1209', 'a1309', 'mo1309']
stripped = [''.join(c for c in s if not c.isdigit()) for s in strings]
1
дададзена

Вы можаце паспрабаваць гэта рэгулярны выраз:

^[a-zA-Z]+

Гэта будзе проста ўзяць паслядоўныя алфавіты ад пачатку і грэбаваць ўсе іншыя рэчы ў радку.

не запатрабуецца Няма замены.

0
дададзена

<�Моцны> Выкарыстанне лустачкі абазначэння, калі даўжыня нумары з'яўляецца фіксаванай і пазіцыя не ў сярэдзіне радка. </Моцны>

NUM_LEN = 4
stringsWithDigit = ["ab1234", "cde1234", "fgh5678"]
for i in stringsWithDigit:
   print i[:-NUM_LEN]

any thing else

import re
c = re.compile("[^0-9]+")
print c.findall("".join(stringsWithDigit))
0
дададзена