Игнорирование всех значений не с плавающей точкой при преобразовании строки в число с плавающей точкой для их суммирования - PullRequest
0 голосов
/ 28 августа 2018

Я пытаюсь преобразовать все строковые значения в плавающие значения для добавления, но в моем csv есть строки, и он возвращает эту ошибку:

L.append([i, j, sum(i for i in map(float, filter(None, 
k)) if i in {0.5, 1, 2})])
ValueError: could not convert string to float: 'l0g0dim'

Как я могу игнорировать строки с буквами, запятыми и другими неконвертируемыми символами и суммировать их без проблем?

Пример файла3.csv

1754|2014-06-13 07:00:00|0|0.5|0
1754|2014-06-13 08:00:00|0|2|0.5
1754|2014-06-13 09:00:00|0|a0|b0|2
1278|2014-01-26 18:00:00|light subcoatal draft ...|0|0|2|0.5
1754|2014-06-04 19:00:00|0|leg dim|0|0
1754|2014-06-13 10:00:00|0|(C) fins|0|0

код

    import csv
    import re
    import time
    from io import StringIO

replacements = (
("(B)", "0"), ("(D)", "1"), ("Entrée air absente", "2"),

("+", "0.5"), ("++", "1"), ("+++", "2"),

("(S) +", "0.5"), ("(S) expi. ++", "1"), ("(S) +++", "2"),

("100", "0"), ("99", "0"), ("98", "0"), ("97", "0"), ("96", "0"),
("95", "0"), ("94", "1"), ("93", "1"),
("92", "1"), ("91", "1"), ("90", "1"), ("89", "1"),
("Bruits de transmission", "0"), ("Fatigué/épuisé", "0"), (" *", "0"), ("tirage sous costal", "0"), ("léger BAN", "0"),   )

replvalues = dict(replacements)
regex = "|".join(map(re.escape,                                 
replvalues.keys()))
repl = lambda x: replvalues.get(x.string[x.start():x.end()])

with open("file3.csv", "r", encoding='utf-8') as f_in, \
    open("file4.csv", "w", encoding='utf-8') as f_out:


    for i in f_in:
        line = re.sub(regex, repl, i)
        f_out.write(line)

with open("file4.csv", "r", encoding='utf-8') as f_in, \
     open("file5.csv", "w", encoding='utf-8') as f_out:
L = []
with f_in as fin:
    reader = csv.reader(fin, delimiter='|')
    for i, j, *k in reader:
      L.append([i, j, sum(i for i in map(float, filter(None, k)) if i in {0.5, 1, 2})])
    f_out.write(L)
print(L)

Ответы [ 2 ]

0 голосов
/ 28 августа 2018

Зачем фильтровать дважды?

filter(None, k)           # filter
(... if i in {0.5, 1, 2}) # another filter

Вы можете отфильтровать один раз и просто удалить не плавающие значения, проверив набор строк на соответствующие значения (значения ожидаемые в вашем CSV):

L.append([i, j, sum(float(i) for x in k if x in {'0.5', '1', '2'})])
                                       #|<-      filter       ->|  

Несовместимые строковые значения, такие как строка 'leg dim', никогда не пройдут фильтр и, следовательно, не попадут в последний вызов float.

0 голосов
/ 28 августа 2018

положить эту часть

for i, j, *k in reader:
    L.append([i, j, sum(i for i in map(float, filter(None, k)) if i in {0.5, 1, 2})])
f_out.write(L)

в try....except -блок с проверкой, является ли желаемое значение плавающим. если да, добавьте, если нет, переходите к следующему значению.

...