2010-04-23 2 views
1

У меня есть Dictлучший способ узнать тип

val_dict - {'val1': 'abcd', 'val': '1234', 'val3': '1234.00', 'val4': '1abcd 2gfff'} 

Все значения в мои ключи строка.

Итак, мой вопрос: как узнать тип для моих значений в dict.

Я имею в виду, если я скажу `int (val_dict ['val1']), дайте мне ошибку.

В основном то, что я пытаюсь сделать, это выяснить, если строка является строка или Int или float.`

if int(val_dict['val1'): 
dosomething 
else if float(val_dict['val1']): 
dosomething 

благодаря

+0

Я предполагаю, что это на самом деле важно для вас будь то ИНТ или плавать? В любом случае обе поддерживают одни и те же операции, хотя, конечно, с разной точностью. – extraneon

+5

Почему они струны? Как они попали в словарь в первую очередь? Почему не были преобразованы в соответствующие объекты * до того, как они были помещены в словарь? –

+0

Код, который дает мне dict, не в моей руке. В принципе, я не могу изменить dict. – laspal

ответ

3

Может быть, это:

is_int = True 
try: 
    as_int = int (val_dict['val1']) 
except ValueError: 
    is_int = False 
    as_float = float (val_dict['val1']) 

if is_int: 
    ... 
else: 
    ... 

Вы можете избавиться от is_int, но тогда в try...except будет много кода (вся обработка поплавков), и я буду чувствовать себя неловко об этом.

+0

Также обратите внимание на комментарий С. Лотта. Возможно, вам это даже не нужно, и вместо этого можно улучшить словарь. – doublep

-1

Простое решение, если у вас слишком много форматов, может включать проверку формата каждого значения.

def intlike(value): 
    return value.isdigit() 
def floatlike(value): 
    import re 
    return re.match("^\d+\.\d+$") 

if intlike(val_dict['val1']): 
    dosomething(int(val_dict['val1'])) 
elif floatlike(val_dict['val1']): 
    somethingelse(float(val_dict['val1'])) 
else: 
    entirelydifferent() 

Однако, это на самом деле проще в использовании рамки исключений Python для некоторых сложных форматов:

def floatlike(value): 
    try: 
     float(value) 
    except ValueError: 
     result = False 
    else: 
     result = True 
    return result 
+0

Вам не нужно использовать регулярное выражение для совпадения с поплавком, и ваше регулярное выражение не будет соответствовать всем возможным поплавкам. Python может принуждать «0». и '.0' как float, а + - для «одного или нескольких предыдущих». – lunixbochs

+0

@lunixbochs: Вот почему я рекомендовал структуру исключений. Однако, если данные поступают из известного источника, это регулярное выражение может очень хорошо совпадать с значениями float; это, конечно, похоже на то, что «+» верно, например, с правой стороны. Кроме того, это дает возможность проверить возможности, которые явно не заданы в вопросе; например, другое регулярное выражение может идентифицировать «1abcd 2gfff» в качестве списка. – eswald

2

Все значения являются конечно «реальных строк» ​​(вы можете делать с ними все, что вы возможно, со строками!), но я думаю, что большинство респондентов знают, что вы имеете в виду, - вы хотите попробовать преобразовать каждое значение в несколько возможных типов поочередно («int» и «float» - это именно то, что вы называете, но не могли есть другие ...?) и вернуться и использовать первое преобразование, которое будет успешным.

Это, конечно, наилучшим образом инкапсулируется функцией, отличной от вашей прикладной логики. Если лучший матч для ваших нужд, это просто сделать преобразование и вернуть «лучший преобразованное значение» (и все они будут использоваться аналогично), то:

def best_convert(s, types=(int, float)): 
    for t in types: 
    try: return t(s) 
    except ValueError: continue 
    return s 

, если вы хотите сделать что-то другое в каждом так, то:

def dispatch(s, defaultfun, typesandfuns): 
    for t, f in typesandfuns: 
    try: 
     v = t(s) 
    except ValueError: 
     continue 
    else: 
     return f(v) 
    return defaultfun(s) 

называться, например, как

r = dispatch(s, asstring, ((int, asint), (float, asfloat))) 

, если функции должны быть вызваны в «неконвертируемых струн», те, конвертируемые в целое, и те, конвертируемые плавать, но не ИНТ , а соответственно asstring, asint, asfloat.

я не рекомендуем помещать «структурные» «пытаются преобразования в этих различных типов, в свою очередь, и действовать соответствующим образом» код в неразрывной смеси с «логикой приложения» - это прозрачный чехол аккуратно наслоения два аспекта, с хорошей структурой и разделением.

0

можно определить, если строка будет преобразовать в междунар или плавать очень легко, без использования исключений

# string has nothing but digits, so it's an int 
if string.isdigit(): 
    int(string) 

# string has nothing but digits and one decimal point, so it's a float 
elif string.replace('.', '', 1).isdigit(): 
    float(string) 
Смежные вопросы