TL; DR :
- Wenn Ihre Eingabe hauptsächlich Zeichenfolgen sind , die in Floats konvertiert werden können, ist die
try: except:
Methode die beste native Python-Methode.
- Wenn es sich bei Ihrer Eingabe hauptsächlich um Zeichenfolgen handelt, die nicht in Floats konvertiert werden können, sind reguläre Ausdrücke oder die Partitionsmethode besser.
- Wenn Sie 1) sich Ihrer Eingabe nicht sicher sind oder mehr Geschwindigkeit benötigen und 2) nichts dagegen haben und eine C-Erweiterung eines Drittanbieters installieren können, funktionieren Fastnumbers sehr gut.
Es gibt eine andere Methode, die über ein Drittanbieter-Modul namens Fastnumbers verfügbar ist (Offenlegung, ich bin der Autor). Es bietet eine Funktion namens isfloat . Ich habe das von Jacob Gabrielson in dieser Antwort skizzierte Beispiel genommen , aber die fastnumbers.isfloat
Methode hinzugefügt . Ich sollte auch beachten, dass Jacobs Beispiel der Regex-Option nicht gerecht wurde, da die meiste Zeit in diesem Beispiel aufgrund des Punktoperators für globale Suchvorgänge aufgewendet wurde ... Ich habe diese Funktion geändert, um einen faireren Vergleich zu ermöglichen try: except:
.
def is_float_try(str):
try:
float(str)
return True
except ValueError:
return False
import re
_float_regexp = re.compile(r"^[-+]?(?:\b[0-9]+(?:\.[0-9]*)?|\.[0-9]+\b)(?:[eE][-+]?[0-9]+\b)?$").match
def is_float_re(str):
return True if _float_regexp(str) else False
def is_float_partition(element):
partition=element.partition('.')
if (partition[0].isdigit() and partition[1]=='.' and partition[2].isdigit()) or (partition[0]=='' and partition[1]=='.' and partition[2].isdigit()) or (partition[0].isdigit() and partition[1]=='.' and partition[2]==''):
return True
else:
return False
from fastnumbers import isfloat
if __name__ == '__main__':
import unittest
import timeit
class ConvertTests(unittest.TestCase):
def test_re_perf(self):
print
print 're sad:', timeit.Timer('ttest.is_float_re("12.2x")', "import ttest").timeit()
print 're happy:', timeit.Timer('ttest.is_float_re("12.2")', "import ttest").timeit()
def test_try_perf(self):
print
print 'try sad:', timeit.Timer('ttest.is_float_try("12.2x")', "import ttest").timeit()
print 'try happy:', timeit.Timer('ttest.is_float_try("12.2")', "import ttest").timeit()
def test_fn_perf(self):
print
print 'fn sad:', timeit.Timer('ttest.isfloat("12.2x")', "import ttest").timeit()
print 'fn happy:', timeit.Timer('ttest.isfloat("12.2")', "import ttest").timeit()
def test_part_perf(self):
print
print 'part sad:', timeit.Timer('ttest.is_float_partition("12.2x")', "import ttest").timeit()
print 'part happy:', timeit.Timer('ttest.is_float_partition("12.2")', "import ttest").timeit()
unittest.main()
Auf meinem Computer lautet die Ausgabe:
fn sad: 0.220988988876
fn happy: 0.212214946747
.
part sad: 1.2219619751
part happy: 0.754667043686
.
re sad: 1.50515985489
re happy: 1.01107215881
.
try sad: 2.40243887901
try happy: 0.425730228424
.
----------------------------------------------------------------------
Ran 4 tests in 7.761s
OK
Wie Sie sehen können, ist Regex nicht so schlecht, wie es ursprünglich schien, und wenn Sie ein echtes Bedürfnis nach Geschwindigkeit haben, ist die fastnumbers
Methode ziemlich gut.