2011-04-09 8 views
9

내가 원했을 때 나는 다른 대답을 찾을 수 없었습니다. 그래서 나는 다른 사람들을 위해 내 자신의 해결책을 게시 할 것이고 또한 내가 잘못한 것을 정정 할 수 있다고 생각했습니다.문자열을 int 또는 float로 변환하려면 어떻게해야합니까?

필자는 자동 구성 파일 파서를 작성해야했으며 가능한 경우 숫자를 int로 만들고 그렇지 않은 경우 float을 선호했습니다. 어떤 float도 int로 강제 변환되기 때문에 일반적인 try/except 변환은 그 자체로는 작동하지 않습니다.

누군가가 묻는 것처럼 명확히하기 위해 기본적으로 숫자는 설정 파일 데이터를 작성하는 사람이 숫자로 변환하도록되어 있습니다. 십진수가있는 것은 플로트가 될 것입니다. 또한 부동 소수점 숫자의 특성으로 인해 부동 소수점은 일부 연산자 (예 : ==, <,>)에 위험 할 수 있으며 필요하면 int가 float로 변환됩니다. 따라서 가능한 경우 정수로 유지하는 것이 더 좋습니다. 큰 일이 아니라 자신을위한 국제 대회의 일종.

+1

[파이썬 - 부동 문자열 또는 부동 문자열 해석] 가능한 복제본 (http://stackoverflow.com/questions/379906/python-parse-string-to-float-or-int) – Johnsyweb

+0

복제본이 아님; 그 질문은 다른 것을 요구합니다. –

+1

질문을 편집하여 "가능한 경우 숫자를 정수로"의미하는 것을 명확하게 보여주는 예제를 제공하십시오. 특히 "10.0000"(사용자의 의도가 분명히 떠있는 부분)을 int 또는 float로 변환하려고합니까? –

답변

21
def int_or_float(s): 
    try: 
     return int(s) 
    except ValueError: 
     return float(s) 

당신이 "10.0000" 같은 것이 int로 변환하려면이 시도 :

당신은 "1e25" 같은 입력을 원하는가
def int_dammit_else_float(s): 
    f = float(s) 
    i = int(f) 
    return i if i == f else f 

어떤 결과?

+0

와우 나는 당신의 첫 번째 해결책이 내가 원했던 바를 정확히 깨달았을 때 어리 석다. 나는 int (1.1)가 int (1.1) 이후 1로 강요 할 것이라는 잘못된 이해하에 일하고있었습니다. 답변을 주셔서 감사 드리며 잘못된 가정을 바로 잡도록 도와줍니다. – KobeJohn

2

이것은 보통 용서를 구하는 것보다 먼저 허가를받는 것이 더 좋으며 보통 일을하는 'Pythonic'방법으로 간주되며 보통 try/except이 포함됩니다. 따라서이 같은 간단한 일이 충분히 좋은 수 있습니다 :

import re 
pattern = re.compile(r'[.eE]') 
v = float(s) if pattern.findall(s) else int(s) 
: 부동 소수점 숫자 신호를 보낼 수 이상의 문자 거기 때문에

v = float(s) if '.' in s or 'e' in s.lower() else int(s) 

, 당신도 그들 중 하나이 다음과 같은 다른 방법을 확인할 수 있습니다

또는

chars = set('.eE') 
v = float(s) if any((c in chars) for c in s) else int(s) 

마지막으로, 약간 다른 트랙에, 당신은 정수가 될 시점 정수를 부동 원한다면, 당신은 @ 존 M과 유사 다음을 할 수 achin의 "_dammit_"기능 :

v = int(float(s)) if int(float(s)) == float(s) else float(s) 
+0

당신이 물어야하는 모든 것을 알고있는 경우에만; "1E-6"을 시도하십시오 –

+0

@ John Machin : 일반적으로 좋은 지적이지만 여기서는 여전히 관리가 가능합니다 (내 업데이트 참조). – martineau

+0

코드 martineau 주셔서 감사합니다. 그것은 내 요구에 아주 잘 작동하고 내가 가지고있는 것을 단순화 할 것이다. 사례를 처리하기 시작하면 모든 경우를 잡기 위해 정규 표현식을 사용하는 것이 더 좋을 것이라고 생각하기 때문에 실제로 E 표기를 생략 할 것입니다. – KobeJohn

2

평가 (들)

eval() 문자열을 받아 파이썬 코드로 처리하는 기능입니다. 어떤 종류의 리터럴이 문자열로 주어진다면, 그 값을 포함하는 파이썬 객체를 리턴 할 것입니다.

그러나 보안 측면에서 볼 때 누군가가 프로그램에 충돌하거나 조작 할 수있는 지침을 제공 할 수 있으므로 이는 잘못된 생각입니다. 다음과 같이 처리하기 전에 일정한 문자 집합을 요구할 수 있습니다. 즉 :

eval(s) if not set(s).difference('.') else None 

이것은 여전히 ​​두통의 가치가 없습니다. 즉, 당신은 공상을 얻을 수 있고, 계산과 함께 표현을 허용 할 수 있습니다 ... 그리고 그것은 시험할만한 가치가있을 것입니다! 전달 된 객체가 INT를 리턴하거나 또는 전환 없음을 떠 위해 상기

num = lambda s: eval(s) if not set(s).difference('. *+-/e') else None 

>>> num('10') 
10 
>>> num('10.0') 
10.0 
>>> num('1e3') 
1000.0 
>>> num('4.8 * 10**34') 
4.8e+34 
>>> num('1+2/3') 
1.6666666666666665 
2
def int_float_none(x): 
    # it may be already int or float 
    if isinstance(x, (int, float)): 
     return x 
    # all int like strings can be converted to float so int tries first 
    try: 
     return int(x) 
    except (TypeError, ValueError): 
     pass 
    try: 
     return float(x) 
    except (TypeError, ValueError): 
     return None 

기능.

관련 문제