analitics

Pages

Monday, July 8, 2019

Python 3.7.3 : Using attrgetter from operator python module.

Return a callable object that fetches attr from its operand. If more than one attribute is requested, returns a tuple of attributes. The attribute names can also contain dots. see documentation.
The attrgetter operator works more or less similar to itemgetter, except that it looks up an attribute instead of an index.
For example to test this operator we need to create a class to access the attribute on the class.
I create a class named Person with name and surname initialization.
I will get the attributes from this class and show it.
C:\Python373>python.exe
Python 3.7.3 (v3.7.3:ef4ec6ed12, Mar 25 2019, 21:26:53) [MSC v.1916 32 bit (Inte
l)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import operator
>>> class Person:
...     def __init__(self, name, surname):
...             self.n = name
...             self.s = surname
...
>>> my_per = Person('Festila', 'Catalin George')
>>> getter = operator.attrgetter("n")
>>> print(getter)
operator.attrgetter('n')
>>> print(getter(my_per))
Festila
>>> another_getter = operator.attrgetter("s")
>>> print(another_getter)
operator.attrgetter('s')
>>> print(another_getter(my_per))
Catalin George
>>> all = operator.attrgetter("n","s")
>>> print(all)
operator.attrgetter('n', 's')
>>> print(all(my_per))
('Festila', 'Catalin George')
To restrict setting an attribute outside of constructor you need to use a private attribute starting with an underscore, and a read-only property for public access.
See the new class with the attribute s restricted:
class Person:
    def __init__(self, name, surname):
            self.n = name
            self.s = surname
s = property(operator.attrgetter("_s"))
Let's test it in another way:
>>> from operator import attrgetter
>>> test=attrgetter('something')
>>> print(test)
operator.attrgetter('something')
>>> print(type(test))

>>> print(test(something))
Traceback (most recent call last):
  File "", line 1, in 
NameError: name 'something' is not defined
>>> print(type(test(something)))
Traceback (most recent call last):
  File "", line 1, in 
NameError: name 'something' is not defined
Because something is not initialized correctly the error is expected for both: test(something) and type(test(something)
>>> something = 'all'
>>> print(type(test))

>>> print(type(test(something)))
Traceback (most recent call last):
  File "", line 1, in 
AttributeError: 'str' object has no attribute 'something'
>>> something = 1
>>> print(type(test(something)))
Traceback (most recent call last):
  File "", line 1, in 
AttributeError: 'int' object has no attribute 'something'