删除所有出现的点,除了列表元素中的第一个匹配项

时间:2015-02-02 18:07:57

标签: python string list

我有一个列表,我需要转换为浮动。由于我没有输入数据,因此有些元素会有意外的额外期间,例如39.04.1450。我需要能够自动删除所有句点,除了显示的第一个句点,以便在我说list=float(list)时我不会收到错误。

示例清单:

latitude= [' -86.57', ' 39.04.1450', ' 37.819' ,' 45.82', ' 54.42', ' 0.' ,' 53.330444',
  ' +45.75' ,' 52.36', ' 43.2167', ' -36.75', ' 6.8N' ,' 40.833' ,' -97.981',
  ' 41.720', ' 41.720', ' 37.41' ,' 37.41' ,' 37.41', ' 37.41']

如您所见,latitude[1]有一个额外的小数点。当然,我还需要在6.8N中删除N,但这是一个单独的问题。

7 个答案:

答案 0 :(得分:4)

我会这样做:

def fix_float(s):
    return s.replace('.', '[DOT]', 1).replace('.', '').replace('[DOT]', '.')

该函数将'.'的第一次出现替换为'[DOT]'。然后,它删除'.'的所有发生。最后,它将'[DOT]'替换为'.'

要将其应用于列表的所有元素,请写下:

fixed_latitudes = [fix_float(s) for s in latitude]

答案 1 :(得分:2)

def my_float(s):
    s=s.split(".")
    return float(".".join([s[0],"".join(s[1:]))])

会分开。并且只重新加入第一个句号...但它不会对-6.8N

做任何事情

答案 2 :(得分:2)

您可以使用regular expressions

import re  

pattern = re.compile(r'(\d+\.\d+)\.')
new_lst = [re.sub(pattern, r'\1', i).replace('N', '') for i in latitude]

\d表示任何数字,+表示一个或多个,\.与点字符匹配。括号正在捕获匹配的那部分,稍后在sub()中使用\1(意味着第一个捕获组)。

答案 3 :(得分:1)

如果您的损坏数据最后只包含N且多个.,那么这是一个小问题...除此之外,您还需要添加更多内容

latitude = [' -86.57', ' 39.04.1450', ' 37.819', ' 45.82', ' 54.42', ' 0.', ' 53.330444', ' +45.75', ' 52.36', ' 43.2167', ' -36.75', ' 6.8N', ' 40.833', ' -97.981', ' 41.720', ' 41.720', ' 37.41', ' 37.41', ' 37.41', ' 37.41']
flist = []
for i in latitude:
    try:
        flist.append(float(i))
    except ValueError:
        if (i[-1] == 'N'):
            flist.append(float(i[:-1]))
        else:
            flist.append(float("{}.{}".format(i.split(".")[0],''.join(i.split(".")[1:]))))

print (flist)

输出

[-86.57, 39.04145, 37.819, 45.82, 54.42, 0.0, 53.330444, 45.75, 52.36, 43.2167, -36.75, 6.8, 40.833, -97.981, 41.72, 41.72, 37.41, 37.41, 37.41, 37.41]

答案 4 :(得分:1)

您可以使用正则表达式从列表中提取数字并立即将它们转换为浮点数。

import re
lat = lambda l: float(re.search('[+-]*\d*\.\d*',l).group(0))
print map(lat,latitude)

编辑:
对不起,我没有注意到,小数点后第二位的数字也是有效的。 一个新的解决方案仍然期望第一个点是可以的,其余的都将被删除。

其中一个值包含N,所以我想可能还有S表示它的南部,即负纬度。因此,我将此假设实现为代码。

def valid_lat(s): a = re.findall('\s*[+-]*\d*\.\d*',s)[0] b = s.lstrip(a) d = b.replace('.','') c = re.sub('[nNsS]$','',d) sign = 1. if re.match('[sS]$',d):sign = -1. return (float(a + c))*sign

然后只是map它:
map(valid_lat,latitude)

答案 5 :(得分:0)

这个怎么样?

def lol_float(_str):
    # check where decimal point is (starting from right) '3.45' -> 2
    dpi = (len(_str) - _str.count('.') - _str.index('.')) if '.' in _str else 0
    # '3.45' -> 345.0
    float_as_int = float(filter(lambda x: x.isdigit(), _str))
    # dpi = 2, float_as_int = 34.0 -> 3.45
    return float_as_int / (10 ** dpi)

输出:

>>> lol_float('3.34')
3.34
>>> lol_float('3.45')
3.45
>>> lol_float('345')
345.0
>>> lol_float('34.5')
34.5
>>> lol_float('3.4.5')
3.45
>>> lol_float('3.45')
3.45
>>> lol_float('345')
345.0
>>> lol_float('3.4..5')
3.45
>>> lol_float('3.4..5.4')
3.454

只是原创......:)

答案 6 :(得分:0)

您可以使用str.rstrip删除任何字母:

from string import ascii_letters

out = []
for x in latitude:
    x = x.rstrip(ascii_letters)
    spl = x.split(".")
    if len(spl) > 2:
        out.append(float("{}.{}".format(spl[0],"".join(spl[1:]))))
    else:
        out.append(float(x)))
print(out)

[-86.57, 39041450.0, 37.819, 45.82, 54.42, 0.0, 53.330444, 45.75, 52.36, 43.2167, -36.75, 6.8, 40.833, -97.981, 41.72, 41.72, 37.41, 37.41, 37.41, 37.41]

您可以在单个列表组件中执行此操作,但效率较低:

print([float(x[::-1].rstrip(ascii_letters).replace(".","")[::-1]) if x.count(".") > 1 else float(x.rstrip(ascii_letters)) for x in latitude ])