Obtener información del objeto (Liao Xuefeng)

Cuando obtenemos una referencia a un objeto, ¿cómo sabemos de qué tipo es este objeto y qué métodos hay?

Use type ()

Primero, determinemos el tipo de objeto y usemos la type()función:

Los tipos básicos se pueden type()juzgar:

>>> type(123)
<class 'int'>
>>> type('str')
<class 'str'>
>>> type(None)
<type(None) 'NoneType'>

Si una variable apunta a una función o clase, también puede usar el type()juicio:

>>> type(abs)
<class 'builtin_function_or_method'>
>>> type(a)
<class '__main__.Animal'>

Pero, type()¿de qué tipo regresa la función? Devuelve el tipo de clase correspondiente. Si queremos ifjuzgar en la declaración, necesitamos comparar si los tipos de tipo de las dos variables son iguales:

>>> type(123)==type(456)
True
>>> type(123)==int
True
>>> type('abc')==type('123')
True
>>> type('abc')==str
True
>>> type('abc')==type(123)
False

Puede escribir directamente el tipo de datos básicos int, stretc., pero ¿qué sucede si desea determinar si un objeto es una función? Puede usar typeslas constantes definidas en el módulo:

>>> import types
>>> def fn():
...     pass
...
>>> type(fn)==types.FunctionType
True
>>> type(abs)==types.BuiltinFunctionType
True
>>> type(lambda x: x)==types.LambdaType
True
>>> type((x for x in range(10)))==types.GeneratorType
True

Use isinstance ()

Para la relación de herencia de clase, type()es muy incómodo de usar . Tenemos que juzgar el tipo de clase, podemos usar isinstance()funciones.

Recordamos el ejemplo anterior, si la relación de herencia es:

object -> Animal -> Dog -> Husky

Entonces, isinstance()podemos decir si un objeto es de cierto tipo. Primero cree tres tipos de objetos:

>>> a = Animal()
>>> d = Dog()
>>> h = Husky()

Entonces, juzgue:

>>> isinstance(h, Husky)
True

No hay problema, porque la hvariable apunta al objeto Husky.

Entonces juzgue:

>>> isinstance(h, Dog)
True

hAunque es un tipo Husky, Husky sigue hsiendo un tipo Dog porque se hereda de Dog . En otras palabras, isinstance()se juzga si un objeto es el tipo en sí mismo o si se encuentra en la cadena de herencia principal del tipo.

Por lo tanto, podemos estar seguros de que hes el tipo Animal:

>>> isinstance(h, Animal)
True

Del mismo modo, el tipo real es el tipo de perro dy animal:

>>> isinstance(d, Dog) and isinstance(d, Animal)
True

Sin embargo, dno el tipo Husky:

>>> isinstance(d, Husky)
False

Disponibles type()tipos básicos de determinación pueden utilizarse isinstance()para determinar:

>>> isinstance('a', str)
True
>>> isinstance(123, int)
True
>>> isinstance(b'a', bytes)
True

Y también puede determinar si una variable es uno de ciertos tipos, como el siguiente código puede determinar si es una lista o una tupla:

>>> isinstance([1, 2, 3], (list, tuple))
True
>>> isinstance((1, 2, 3), (list, tuple))
True
Utilice siempre isinstance () para determinar el tipo, y puede "especificar todos los tipos" del tipo especificado y sus subclases.

Usar dir ()

Si desea obtener todas las propiedades y métodos de un objeto, puede usar una dir()función, que devuelve una lista que contiene cadenas, por ejemplo, para obtener todas las propiedades y métodos de un objeto str:

>>> dir('ABC')
['__add__', '__class__',..., '__subclasshook__', 'capitalize', 'casefold',..., 'zfill']

__xxx__Propiedades y métodos similares tienen usos especiales en Python, como la __len__longitud de retorno del método. En Python, si llama a una len()función para intentar obtener la longitud de un objeto, de hecho, dentro de la len()función, llama automáticamente al __len__()método del objeto , por lo que el siguiente código es equivalente:

>>> len('ABC')
3
>>> 'ABC'.__len__()
3

Si queremos usar la clase que escribimos len(myObj)nosotros mismos, escriba un __len__()método por nosotros mismos :

>>> class MyDog(object):
...     def __len__(self):
...         return 100
...
>>> dog = MyDog()
>>> len(dog)
100

El resto son atributos o métodos comunes, como lower()devolver una cadena en minúsculas:

>>> 'ABC'.lower()
'abc'

Sólo las propiedades y métodos enumerados no es suficiente para satisfacer getattr(), setattr()y hasattr()que pueden manipular directamente el estado de un objeto:

>>> class MyObject(object):
...     def __init__(self):
...         self.x = 9
...     def power(self):
...         return self.x * self.x
...
>>> obj = MyObject()

A continuación, puede probar las propiedades del objeto:

>>> hasattr(obj, 'x') # 有属性'x'吗?
True
>>> obj.x
9
>>> hasattr(obj, 'y') # 有属性'y'吗?
False
>>> setattr(obj, 'y', 19) # 设置一个属性'y'
>>> hasattr(obj, 'y') # 有属性'y'吗?
True
>>> getattr(obj, 'y') # 获取属性'y'
19
>>> obj.y # 获取属性'y'
19

Si intenta obtener un atributo inexistente, se generará un AttributeError:

>>> getattr(obj, 'z') # 获取属性'z'
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'MyObject' object has no attribute 'z'

Puede pasar un parámetro predeterminado, si el atributo no existe, devuelve el valor predeterminado:

>>> getattr(obj, 'z', 404) # 获取属性'z',如果不存在,返回默认值404
404

También puede obtener el método del objeto:

>>> hasattr(obj, 'power') # 有属性'power'吗?
True
>>> getattr(obj, 'power') # 获取属性'power'
<bound method MyObject.power of <__main__.MyObject object at 0x10077a6a0>>
>>> fn = getattr(obj, 'power') # 获取属性'power'并赋值到变量fn
>>> fn # fn指向obj.power
<bound method MyObject.power of <__main__.MyObject object at 0x10077a6a0>>
>>> fn() # 调用fn()与调用obj.power()是一样的
81

Resumen

A través de una serie de funciones integradas, podemos analizar cualquier objeto de Python y obtener sus datos internos. Cabe señalar que solo cuando no se conoce la información del objeto, obtendremos la información del objeto. Si puedes escribir directamente:

sum = obj.x + obj.y

Solo no escribas:

sum = getattr(obj, 'x') + getattr(obj, 'y')

Un ejemplo de uso correcto es el siguiente:

def readImage(fp):
    if hasattr(fp, 'read'):
        return readData(fp)
    return None

Supongamos que queremos leer la imagen de la secuencia de archivos fp, primero tenemos que determinar si el objeto fp tiene un método de lectura, si existe, el objeto es una secuencia, si no existe, no se puede leer. hasattr()Fue muy útil.

Tenga en cuenta que en lenguajes dinámicos como Python, existen read()métodos de acuerdo con el tipo de pato, lo que no significa que el objeto fp sea un flujo de archivos, también puede ser un flujo de red o un flujo de bytes en la memoria, pero siempre que el read()método regrese Lo que son datos de imagen válidos, no afecta la función de lectura de la imagen.

Código fuente de referencia

get_type.py

attrs.py

17 artículos originales publicados · Me gusta1 · Visitas 819

Supongo que te gusta

Origin blog.csdn.net/weixin_45433031/article/details/105013320
Recomendado
Clasificación