¿Cómo convertir Nonetype a int o string?

Tengo un valor de Nonetype x , generalmente es un número, pero podría ser None . Quiero dividirlo por un número, pero Python plantea:

 TypeError: int() argument must be a string or a number, not 'NoneType' 

¿Como puedo resolver esto?

En uno de los comentarios, usted dice:

De alguna manera obtuve un valor de Nonetype, se supone que es un int, pero ahora es un objeto Nonetype

Si es su código, averigüe cómo obtiene None cuando espera un número y evite que eso suceda.

Si es el código de otra persona, averigüe las condiciones en las que no da None y determine un valor razonable para usar con el código condicional habitual:

 result = could_return_none(x) if result is None: result = DEFAULT_VALUE 

…o incluso…

 if x == THING_THAT_RESULTS_IN_NONE: result = DEFAULT_VALUE else: result = could_return_none(x) # But it won't return None, because we've restricted the domain. 

No hay ninguna razón para usar 0 aquí de forma automática: las soluciones que dependen de la “falsedad” de None suponen que querrá esto. El DEFAULT_VALUE (si existe) depende completamente del propósito de su código.

 int(value or 0) 

Esto usará 0 en el caso cuando proporcione cualquier valor que Python considere False , como Ninguno, 0, [], “”, etc. Dado que 0 es False , solo debe usar 0 como valor alternativo (de lo contrario encontrará tus 0s se están convirtiendo en ese valor).

 int(0 if value is None else value) 

Esto reemplaza a None con 0. Ya que estamos None específicamente para None , puede usar algún otro valor como reemplazo.

Una forma común “Pythonic” para manejar este tipo de situación se conoce como EAFP por ” Es más fácil pedir perdón que permiso “. Lo que generalmente significa escribir código que asume que todo está bien, pero luego envolverlo con un bloque try..except en caso de que se manejen las cosas cuando no lo está.

Aquí está el estilo de encoding aplicado a su problema:

 try: my_value = int(my_value) except TypeError: my_value = 0 # or whatever you want to do answer = my_value / divisor 

O quizás el más simple y un poco más rápido:

 try: answer = int(my_value) / divisor except TypeError: answer = 0 

El enfoque inverso y más tradicional se conoce como LBYL que significa ” Mira antes de saltar ” es lo que @Soviut y algunos de los otros han sugerido. Para una cobertura adicional de este tema, vea mi respuesta y los comentarios asociados a la pregunta Determine si una clave está presente en un diccionario en otra parte de este sitio.

Un problema potencial con EAFP es que puede ocultar el hecho de que algo está mal con alguna otra parte de su código o módulo de terceros que está utilizando, especialmente cuando las excepciones ocurren con frecuencia (y por lo tanto no son casos realmente “excepcionales”) en absoluto).

Ese TypeError solo aparece cuando intentas pasar int() None (que es el único valor NoneType , que yo sepa). Yo diría que su objective real no debería ser convertir NoneType en int o str , sino averiguar dónde / por qué está obteniendo None lugar de un número como se esperaba, y corregirlo o manejar el None correctamente.

He utilizado con éxito int (x o 0) para este tipo de error, siempre y cuando Ninguno debe ser igual a 0 en la lógica. Tenga en cuenta que esto también se resolverá en 0 en otros casos donde las pruebas x devuelvan Falso. Por ejemplo, lista vacía, conjunto, diccionario o cadena de longitud cero. Lo siento, Kindall ya dio esta respuesta.

Esto puede suceder si olvida devolver un valor desde una función: luego devuelve Ninguno. Mire todos los lugares donde está asignando esa variable y vea si uno de ellos es una llamada de función donde la función carece de una statement de retorno.

Debe verificar que el valor no sea Ninguno antes de intentar realizar cualquier cálculo en él:

 my_value = None if my_value is not None: print int(my_value) / 2 

Nota: my_value se estableció intencionalmente en Ninguno para probar que el código funciona y que se está realizando la verificación.

Estaba teniendo el mismo problema con las funciones de correo electrónico de Python. A continuación se muestra el código que estaba tratando de recuperar el asunto del correo electrónico en una variable. Esto funciona bien para la mayoría de los correos electrónicos y la variable se llena. Si recibe un correo electrónico de Yahoo o similar y el remitente no completó la línea de asunto, Yahoo no creará una línea de asunto en el correo electrónico y obtendrá un tipo de respuesta de la función. Martineau proporcionó una respuesta correcta, así como Soviut. La respuesta de IMO Soviut es más concisa desde el punto de vista de la progtwigción; no necesariamente de uno de Python. Aquí hay un código para mostrar la técnica:

 import sys, email, email.Utils afile = open(sys.argv[1], 'r') m = email.message_from_file(afile) subject = m["subject"] # Soviut's Concise test for unset variable. if subject is None: subject = "[NO SUBJECT]" # Alternative way to test for No Subject created in email (Thanks for NoneThing Yahoo!) try: if len(subject) == 0: subject = "[NO SUBJECT]" except TypeError: subject = "[NO SUBJECT]" print subject afile.close() 

En Python 3 puedes usar la palabra clave “o” también. De esta manera:

 foo = bar or 0 foo2 = bar or "" 

En algunas situaciones, es útil tener una función para convertir Ninguno a int cero:

 def nz(value): ''' Convert None to int zero else return value. ''' if value == None: return 0 return value