TypeError with objects


Since methods are functions in an object I can assume that they have the same behavior as what I tested in the functions project.


preview

I have these tests by the end of the chapter

questions about TypeError with objects


open the project


test_type_error_w_object_methods

RED: make it fail


I add a test with a call to AnObject.method from tests/test_type_error.py

83    src.type_error.function_08(
84        'positional',
85        argument='keyword',
86    )
87
88
89def test_type_error_w_object_methods():
90    src.type_error.AnObject.method_00()
91
92
93# Exceptions seen

the terminal is my friend, and shows AttributeError

AttributeError: module 'src.type_error'
                has no attribute 'AnObject'

because AnObject is not defined in src/type_error/__init__.py.


GREEN: make it pass


  • I open __init__.py from the type_error folder in the src folder

  • I add a object definition for AnObject to src/type_error/__init__.py

    40def function_08(name, argument):
    41    return None
    42
    43
    44class AnObject(object):
    45
    46    pass
    

    the terminal is my friend, and shows AttributeError

    AttributeError: type object 'AnObject' has no attribute 'method_00'
    

    because there is nothing named method_00 in AnObject.

  • I add the name to the object definition

    44class AnObject(object):
    45
    46    # pass
    47    method_00
    

    the terminal is my friend, and shows NameError

    NameError: name 'method_00' is not defined
    
  • I define method_00 by pointing it to None

    44class AnObject(object):
    45
    46    # pass
    47    # method_00
    48    method_00 = None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'NoneType' object is not callable
    

    because method_00 points to None and I cannot call None like a function.

  • I change method_00 to a method

    44class AnObject(object):
    45
    46    # pass
    47    # method_00
    48    # method_00 = None
    49    def method_00(): return None
    

    the test passes.


REFACTOR: make it better


  • I remove the commented lines from src/type_error/__init__.py

    44class AnObject(object):
    45
    46    def method_00(): return None
    
  • I add a call to src.type_error.AnObject().method_01 from tests/test_type_error.py

    89def test_type_error_w_object_methods():
    90    src.type_error.AnObject.method_00()
    91    src.type_error.AnObject().method_01()
    92
    93
    94# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: 'AnObject' object
                    has no attribute 'method_01'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_01 to AnObject in src/type_error/__init__.py

    44class AnObject(object):
    45
    46    def method_00(): return None
    47    def method_01(): return None
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_01() takes
               0 positional arguments but 1 was given
    

    because a method of an instance takes the instance of the class (self) it belongs to as the first argument.

  • I add @staticmethod to method_01

    class AnObject(object):
    
        def method_00(): return None
    
        @staticmethod
        def method_01(): return None
    

    the test passes because I can use the staticmethod decorator if I do not want to add self to the method definition when it does not use anything that belongs to the object.

    Both methods look the same. The difference is in how I call them AnObject.method_00() vs AnObject().method_01().

  • I add a call to src.type_error.AnObject().method_02 from tests/test_type_error.py

    89def test_type_error_w_object_methods():
    90    src.type_error.AnObject.method_00()
    91    src.type_error.AnObject().method_01()
    92    src.type_error.AnObject().method_02()
    93
    94
    95# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: 'AnObject' object
                    has no attribute 'method_02'.
                    Did you mean: 'method_00'?
    
  • I add a definition for method_02 to AnObject in src/type_error/__init__.py

    44class AnObject(object):
    45
    46    def method_00(): return None
    47
    48    @staticmethod
    49    def method_01(): return None
    50
    51    def method_02(): return self.method_01()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_02() takes
               0 positional arguments but 1 was given
    

    because a method of an instance takes the instance of the class (self) it belongs to as the first argument.

  • I add @staticmethod to method_02

    48    @staticmethod
    49    def method_01(): return None
    50
    51    @staticmethod
    52    def method_02(): return self.method_01()
    

    the terminal is my friend, and shows NameError

    NameError: name 'self' is not defined
    
  • I add self to the parentheses of method_02

    51    @staticmethod
    52    # def method_02(): return self.method_01()
    53    def method_02(self):
    54        return self.method_01()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_02() missing
               1 required positional argument: 'self'
    
  • I comment out the staticmethod decorator

    51    # @staticmethod
    52    # def method_02(): return self.method_01()
    53    def method_02(self):
    54        return self.method_01()
    

    the test passes because a method of an instance takes the instance of the class (self) it belongs to as the first argument which allows it to use things that belong to the object.

  • I add a call to src.type_error.AnObject.method_03 from tests/test_type_error.py

    89def test_type_error_w_object_methods():
    90    src.type_error.AnObject.method_00()
    91    src.type_error.AnObject().method_01()
    92    src.type_error.AnObject().method_02()
    93    src.type_error.AnObject.method_03()
    94
    95
    96# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: type object 'AnObject'
                    has no attribute 'method_03'.
                    Did you mean: 'method_00'?
    
  • I add a definition for method_03 to AnObject in src/type_error/__init__.py

    51    # @staticmethod
    52    # def method_02(): return self.method_01()
    53    def method_02(self):
    54        return self.method_01()
    55
    56    def method_03():
    57        return method_02()
    

    the terminal is my friend, and shows NameError

    NameError: name 'method_02' is not defined
    

    because there is nothing named method_02 inside method_03 or at the module level of src/type_error/__init__.py.

  • I add AnObject. before method_02

    56    def method_03():
    57        # return method_02()
    58        return AnObject.method_02()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_02() missing
               1 required positional argument: 'self'
    

    because

  • I use an instance of the class to call the method

    56    def method_03():
    57        # return method_02()
    58        # return AnObject.method_02()
    59        return AnObject().method_02()
    

    the test passes. This is a silly example because I used AnObject() inside a method of AnObject. I could just use self. I would only need this if I was calling a method of a different object.

  • Here is another silly example. I add a call to src.type_error.AnObject.method_04 from tests/test_type_error.py

    92    src.type_error.AnObject().method_02()
    93    src.type_error.AnObject.method_03()
    94    src.type_error.AnObject.method_04()
    95
    96
    97# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: type object 'AnObject'
                    has no attribute 'method_04'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_04 to AnObject in src/type_error/__init__.py

    56    def method_03():
    57        # return method_02()
    58        # return AnObject.method_02()
    59        return AnObject().method_02()
    60
    61    def method_04():
    62        return AnObject.method_02()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_02() missing
               1 required positional argument: 'self'
    

    because

  • I pass AnObject as input in the call to method_02

    61    def method_04():
    62        # return AnObject.method_02()
    63        return AnObject.method_02(AnObject)
    

    the test passes. I called a method of AnObject and passed AnObject as input. I can use self.

  • I add a call to src.type_error.AnObject().method_05 from tests/test_type_error.py

    93    src.type_error.AnObject.method_03()
    94    src.type_error.AnObject.method_04()
    95    src.type_error.AnObject().method_05()
    96
    97
    98# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: 'AnObject' object
                    has no attribute 'method_05'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_05 to AnObject in src/type_error/__init__.py

    61    def method_04():
    62        # return AnObject.method_02()
    63        return AnObject.method_02(AnObject)
    64
    65    def method_05():
    66        return method_02()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_05() takes
               0 positional arguments but 1 was given
    

    because a method of an instance takes the instance of the class (self) it belongs to as the first argument.

  • I add self to the parentheses of method_05

    65    # def method_05():
    66    def method_05(self):
    67        return method_02()
    

    the terminal is my friend, and shows NameError

    NameError: name 'method_02' is not defined
    

    because there is no method_02 at the module level of src/type_error/__init__.py. It is inside AnObject in src/type_error/__init__.py, I have to be specific.

  • I add self. before method_02

    65    # def method_05():
    66    def method_05(self):
    67        # return method_02()
    68        return self.method_02()
    

    the test passes.

  • I add a call to src.type_error.AnObject().method_06 from tests/test_type_error.py

    94    src.type_error.AnObject.method_04()
    95    src.type_error.AnObject().method_05()
    96    src.type_error.AnObject().method_06()
    97
    98
    99# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: 'AnObject' object
                    has no attribute 'method_06'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_06 to AnObject in src/type_error/__init__.py

    65    # def method_05():
    66    def method_05(self):
    67        # return method_02()
    68        return self.method_02()
    69
    70    def method_06():
    71        return self.method_01()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_06() takes
               0 positional arguments but 1 was given
    

    because a method of an instance takes the instance of the class (self) it belongs to as the first argument.

  • I add self to the parentheses of method_06

    70    # def method_06():
    71    def method_06(self):
    72        return self.method_01()
    

    the test passes.

  • I add a call to src.type_error.AnObject().method_07 from tests/test_type_error.py

     95    src.type_error.AnObject().method_05()
     96    src.type_error.AnObject().method_06()
     97    src.type_error.AnObject.method_07()
     98
     99
    100# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: type object 'AnObject'
                    has no attribute 'method_07'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_07 to AnObject in src/type_error/__init__.py

    70    # def method_06():
    71    def method_06(self):
    72        return self.method_01()
    73
    74    def method_07(self):
    75        return self.method_00()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_07() missing
               1 required positional argument: 'self'
    

    because

  • I use an instance of the class to call the method from tests/test_type_error.py

     95    src.type_error.AnObject().method_05()
     96    src.type_error.AnObject().method_06()
     97    # src.type_error.AnObject.method_07()
     98    src.type_error.AnObject().method_07()
     99
    100
    101# Exceptions seen
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_00() takes
               0 positional arguments but 1 was given
    

    because

    • method_00 takes no input (the parentheses are empty).

    • I called it with an instance of the class (AnObject()) which passes the instance as input.

  • I add the staticmethod decorator to method_00 of AnObject in src/type_error/__init__.py

    44class AnObject(object):
    45
    46    @staticmethod
    47    def method_00(): return None
    

    the test passes. I can use the staticmethod decorator if I do not want to add self to the method definition when it does not use anything that belongs to the object.

  • I add a call to src.type_error.AnObject.method_08() from tests/test_type_error.py

     97    # src.type_error.AnObject.method_07()
     98    src.type_error.AnObject().method_07()
     99    src.type_error.AnObject.method_08()
    100
    101
    102# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: type object 'AnObject'
                    has no attribute 'method_08'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_08 to AnObject in src/type_error/__init__.py

    75    def method_07(self):
    76        return self.method_00()
    77
    78    def method_08(self):
    79        return self.method_04()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_08() missing
               1 required positional argument: 'self'
    

    because I called method_08 like a staticmethod and it is defined as an instance method (It expects self as input).

  • I use an instance of the class to call the method from tests/test_type_error.py

     97    # src.type_error.AnObject.method_07()
     98    src.type_error.AnObject().method_07()
     99    # src.type_error.AnObject.method_08()
    100    src.type_error.AnObject().method_08()
    101
    102
    103# Exceptions seen
    

    the terminal shows TypeError

    TypeError: AnObject.method_04() takes
               0 positional arguments but 1 was given
    

    because

    • method_04 takes no input (the parentheses are empty).

    • I called it with an instance of the class (AnObject()) which passes the instance as input.

  • I add the staticmethod decorator to method_04 of AnObject in src/type_error/__init__.py

    57    def method_03():
    58        # return method_02()
    59        # return AnObject.method_02()
    60        return AnObject().method_02()
    61
    62    @staticmethod
    63    def method_04():
    64        # return AnObject.method_02()
    65        return AnObject.method_02(AnObject)
    66
    67    # def method_05():
    68    def method_05(self):
    69        # return method_02()
    70        return self.method_02()
    

    the test passes.

  • I add a call to src.type_error.AnObject().method_09() from tests/test_type_error.py

     99    # src.type_error.AnObject.method_08()
    100    src.type_error.AnObject().method_08()
    101    src.type_error.AnObject().method_09()
    102
    103
    104# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: 'AnObject' object
                    has no attribute 'method_09'.
                    Did you mean: 'method_00'?
    
  • I add a method definition for method_09 to AnObject in src/type_error/__init__.py

    79    def method_08(self):
    80        return self.method_04()
    81
    82    def method_09(self):
    83        return self.method_03()
    

    the terminal is my friend, and shows TypeError

    TypeError: AnObject.method_03() takes
               0 positional arguments but 1 was given
    

    because

    • method_03 takes no input (the parentheses are empty).

    • I called it with an instance of the class (AnObject()) which passes the instance as input.

  • I add the @staticmethod to method_03 of AnObject in src/type_error/__init__.py

    52    # @staticmethod
    53    # def method_02(): return self.method_01()
    54    def method_02(self):
    55        return self.method_01()
    56
    57    @staticmethod
    58    def method_03():
    59        # return method_02()
    60        # return AnObject.method_02()
    61        return AnObject().method_02()
    62
    63    @staticmethod
    64    def method_04():
    65        # return AnObject.method_02()
    66        return AnObject.method_02(AnObject)
    

    the test passes.

  • I remove the commented lines from src/type_error/__init__.py

    44class AnObject(object):
    45
    46    @staticmethod
    47    def method_00(): return None
    48
    49    @staticmethod
    50    def method_01(): return None
    51
    52    def method_02(self):
    53        return self.method_01()
    
    55    @staticmethod
    56    def method_03():
    57        return AnObject().method_02()
    58
    59    @staticmethod
    60    def method_04():
    61        return AnObject.method_02(AnObject)
    62
    63    def method_05(self):
    64        return self.method_02()
    
    66    def method_06(self):
    67        return self.method_01()
    68
    69    def method_07(self):
    70        return self.method_00()
    71
    72    def method_08(self):
    73        return self.method_04()
    74
    75    def method_09(self):
    76        return self.method_03()
    
  • I remove the commented lines from tests/test_type_error.py

     89def test_type_error_w_object_methods():
     90    src.type_error.AnObject.method_00()
     91    src.type_error.AnObject().method_01()
     92    src.type_error.AnObject().method_02()
     93    src.type_error.AnObject.method_03()
     94    src.type_error.AnObject.method_04()
     95    src.type_error.AnObject().method_05()
     96    src.type_error.AnObject().method_06()
     97    src.type_error.AnObject().method_07()
     98    src.type_error.AnObject().method_08()
     99    src.type_error.AnObject().method_09()
    100
    101
    102# Exceptions seen
    
  • I open a new terminal then make sure I am in the type_error folder

    cd type_error
    
  • I add a git commit message in the other terminal

    git commit --all --message \
    'add test_type_error_w_object_methods'
    

test_type_error_w_the_uncallables

Is every object callable?


RED: make it fail


  • I go back to the terminal that is running the tests.

  • I add a test to tests/test_type_error.py

     99    src.type_error.AnObject().method_09()
    100
    101
    102def test_type_error_w_the_uncallables():
    103    src.type_error.none()
    104
    105
    106# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error' has no attribute 'none'
    

    there is nothing named none in src/type_error/__init__.py in the src folder, yet.


GREEN: make it pass


  • I add none and point it to None

    1none = None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'NoneType' object is not callable
    
    • the () to the right of src.type_error.none makes it a call

    • the name none points to None which is NOT callable. Using substitution

      none = None   # point the name to the object
      none()        # call the name
      None()        # substitute the value for the name
      

      None() raises TypeError because I cannot call None like a function.

  • I make none a function in src/type_error/__init__.py to make it callable

    1# none = None
    2def none(): return None
    3
    4
    5def function_00(the_input):
    6    return None
    

    the test passes.

I can call a function, I cannot call None.


REFACTOR: make it better


  • I add a call to false in tests/test_type_error.py

    101def test_type_error_w_the_uncallables():
    102    src.type_error.none()
    103    src.type_error.false()
    104
    105
    106# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'false'
    

    false is not in src/type_error/__init__.py.

  • I add false to src/type_error/__init__.py and point it to False

    1# none = None
    2def none(): return None
    3false = False
    4
    5
    6def function_00(the_input):
    7    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'bool' object is not callable
    

    false points to False which is NOT callable. Using substitution

    false = False
    false()
    False()
    

    False() raises TypeError because I cannot call a boolean like a function.

  • I change false from a variable to a function to make it callable

    1# none = None
    2def none(): return None
    3# false = False
    4def false(): return False
    5
    6
    7def function_00(the_input):
    8    return None
    

    the test is green again.

  • I add a call to the other boolean in tests/test_type_error.py

    101def test_type_error_w_the_uncallables():
    102    src.type_error.none()
    103    src.type_error.false()
    104    src.type_error.true()
    105
    106
    107# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'true'
    

    there is nothing named true in src/type_error/__init__.py.

  • I add true and point it to True in src/type_error/__init__.py

    3# false = False
    4def false(): return False
    5true = True
    6
    7
    8def function_00(the_input):
    9    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'bool' object is not callable
    
  • I change true from a variable to a function to make it callable

     3# false = False
     4def false(): return False
     5# true = True
     6def true(): return True
     7
     8
     9def function_00(the_input):
    10    return None
    

    the test passes. I can call a function, I cannot call a boolean or None.


  • I add a call to an integer, in tests/test_type_error.py

    103    src.type_error.false()
    104    src.type_error.true()
    105    src.type_error.an_integer()
    106
    107
    108# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'an_integer'
    
  • I add an_integer and point it to 1234 in src/type_error/__init__.py

     5# true = True
     6def true(): return True
     7an_integer = 1234
     8
     9
    10def function_00(the_input):
    11    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'int' object is not callable
    

    the name an_integer points to an integer (1234) which is NOT callable. Using substitution

    an_integer = 1234  # point the name to the object
    an_integer()       # call the name
    1234()             # substitute the value for the name
    

    1234() raises TypeError because I cannot call an integer like a function.

  • I change an_integer from a variable to a function to make it callable

     5# true = True
     6def true(): return True
     7# an_integer = 1234
     8def an_integer(): return 1234
     9
    10
    11def function_00(the_input):
    12    return None
    

    the test passes. I can call a function, I cannot call an integer, a boolean or None.

  • I add a call to a float in tests/test_type_error.py

    104    src.type_error.true()
    105    src.type_error.an_integer()
    106    src.type_error.a_float()
    107
    108
    109# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'a_float'
    
  • I add a_float and point it to 5.678 in src/type_error/__init__.py

     7# an_integer = 1234
     8def an_integer(): return 1234
     9a_float = 5.678
    10
    11
    12def function_00(the_input):
    13    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'float' object is not callable
    

    a_float points to a float (5.678) which is NOT callable. Using substitution

    a_float = 5.678
    a_float()
    5.678()
    

    5.678() raises TypeError because I cannot call a float like a function.

  • I change a_float from a variable to a function to make it callable

     7# an_integer = 1234
     8def an_integer(): return 1234
     9# a_float = 5.678
    10def a_float(): return 5.678
    11
    12
    13def function_00(the_input):
    14    return None
    

    the test passes. I can call a function, I cannot call a float, integer, boolean or None.

  • I add a call to a string (anything in quotes) in tests/test_type_error.py

    105    src.type_error.an_integer()
    106    src.type_error.a_float()
    107    src.type_error.a_string()
    108
    109
    110# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'a_string'
    
  • I add a_string and point it to 'a string' in src/type_error/__init__.py

     9# a_float = 5.678
    10def a_float(): return 5.678
    11a_string = 'a string'
    12
    13
    14def function_00(the_input):
    15    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'str' object is not callable
    

    the name a_string points to a string ('a string') which is NOT callable. Using substitution

    a_string = 'a string' # point the name to the object
    a_string()            # call the name
    'a string'()          # substitute the value for the name
    

    'a string'() raises TypeError because I cannot call a string like a function.

  • I change a_string from a variable to a function to make it callable

     9# a_float = 5.678
    10def a_float(): return 5.678
    11# a_string = 'a string'
    12def a_string(): return 'a string'
    13
    14
    15def function_00(the_input):
    16    return None
    

    the test passes. I can call a function, I cannot call a string, float, integer, boolean or None.

  • I add a call to a tuple (anything in parentheses (), separated by a comma) in tests/test_type_error.py

    106    src.type_error.a_float()
    107    src.type_error.a_string()
    108    src.type_error.a_tuple()
    109
    110
    111# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'a_tuple'
    
  • I add a_tuple and point it to (0, 1, 2, 'n') in src/type_error/__init__.py

    11# a_string = 'a string'
    12def a_string(): return 'a string'
    13a_tuple = (0, 1, 2, 'n')
    14
    15
    16def function_00(the_input):
    17    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'tuple' object is not callable
    

    the name a_tuple points to a tuple ((0, 1, 2, 'n')) which is NOT callable. Using substitution

    a_tuple = (0, 1, 2, 'n')
    a_tuple()
    (0, 1, 2, 'n')()
    

    (0, 1, 2, 'n')() raises TypeError because I cannot call a tuple like a function.

  • I change a_tuple from a variable to a function to make it callable

    11# a_string = 'a string'
    12def a_string(): return 'a string'
    13# a_tuple = (0, 1, 2, 'n')
    14def a_tuple(): return (0, 1, 2, 'n')
    15
    16
    17def function_00(the_input):
    18    return None
    

    the test passes. I can call a function, I cannot call a tuple, string, float, integer, boolean or None.

  • I add a call to a list in tests/test_type_error.py

    107    src.type_error.a_string()
    108    src.type_error.a_tuple()
    109    src.type_error.a_list()
    110
    111
    112# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'a_list'
    
  • I add a_list and point it to [0, 1, 2, 'n'] in src/type_error/__init__.py

    13# a_tuple = (0, 1, 2, 'n')
    14def a_tuple(): return (0, 1, 2, 'n')
    15a_list = [0, 1, 2, 'n']
    16
    17
    18def function_00(the_input):
    19    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'list' object is not callable
    

    a_list points to a list ([0, 1, 2, 'n']) which is NOT callable. Using substitution

    a_list = [0, 1, 2, 'n']
    a_list()
    [0, 1, 2, 'n']()
    

    [0, 1, 2, 'n']() raises TypeError because I cannot call a list like a function.

  • I change a_list from a variable to a function to make it callable

    13# a_tuple = (0, 1, 2, 'n')
    14def a_tuple(): return (0, 1, 2, 'n')
    15# a_list = [0, 1, 2, 'n']
    16def a_list(): return [0, 1, 2, 'n']
    17
    18
    19def function_00(the_input):
    20    return None
    

    the test passes. I can call a function, I cannot call a list, tuple, string, float, integer, boolean or None.

  • I add a call to a set in tests/test_type_error.py

    108    src.type_error.a_tuple()
    109    src.type_error.a_list()
    110    src.type_error.a_set()
    111
    112
    113# Exceptions seen
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'a_set'
    
  • I add a_set and point it to {0, 1, 2, 'n'} in src/type_error/__init__.py

    15# a_list = [0, 1, 2, 'n']
    16def a_list(): return [0, 1, 2, 'n']
    17a_set = {0, 1, 2, 'n'}
    18
    19
    20def function_00(the_input):
    21    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'set' object is not callable
    

    a_set points to a set ({0, 1, 2, 'n'}) which is NOT callable. Using substitution

    a_set = {0, 1, 2, 'n'}
    a_set()
    {0, 1, 2, 'n'}()
    

    {0, 1, 2, 'n'}() raises TypeError because I cannot call a set like a function.

  • I change a_set from a variable to a function to make it callable

    15# a_list = [0, 1, 2, 'n']
    16def a_list(): return [0, 1, 2, 'n']
    17# a_set = {0, 1, 2, 'n'}
    18def a_set(): return {0, 1, 2, 'n'}
    19
    20
    21def function_00(the_input):
    22    return None
    

    the test passes. I can call a function, I cannot call a set, list, tuple, string, float, integer, boolean or None.

  • I add a call to a dictionary in tests/test_type_error.py

    109    src.type_error.a_list()
    110    src.type_error.a_set()
    111    src.type_error.a_dictionary()
    112
    113
    114# Exceptions seen
    115# AssertionError
    116# NameError
    117# TypeError
    118# AttributeError
    

    the terminal is my friend, and shows AttributeError

    AttributeError: module 'src.type_error'
                    has no attribute 'a_dictionary'
    
  • I add a_dictionary and point it to {'key': 'value'} in src/type_error/__init__.py

    17# a_set = {0, 1, 2, 'n'}
    18def a_set(): return {0, 1, 2, 'n'}
    19a_dictionary = {'key': 'value'}
    20
    21
    22def function_00(the_input):
    23    return None
    

    the terminal is my friend, and shows TypeError

    TypeError: 'dict' object is not callable
    

    a_dictionary points to a dictionary ({'key': 'value'}) which is NOT callable. Using substitution

    a_dictionary = {'key': 'value'}
    a_dictionary()
    {'key': 'value'}()
    

    {'key': 'value'}() raises TypeError because I cannot call a dictionary like a function.

  • I change a_dictionary from a variable to a function to make it callable

    17# a_set = {0, 1, 2, 'n'}
    18def a_set(): return {0, 1, 2, 'n'}
    19# a_dictionary = {'key': 'value'}
    20def a_dictionary(): return {'key': 'value'}
    21
    22
    23def function_00(the_input):
    24    return None
    

    the test is green again. I can call a function, I cannot call a dictionary, set, list, tuple, string, float, integer, boolean or None.

  • I remove the commented lines from src/type_error/__init__.py

     1def none(): return None
     2def false(): return False
     3def true(): return True
     4def an_integer(): return 1234
     5def a_float(): return 5.678
     6def a_string(): return 'a string'
     7def a_tuple(): return (0, 1, 2, 'n')
     8def a_list(): return [0, 1, 2, 'n']
     9def a_set(): return {0, 1, 2, 'n'}
    10def a_dictionary(): return {'key': 'value'}
    11
    12
    13def function_00(the_input):
    14    return None
    
  • I add a git commit message in the other terminal

    git commit --all --message \
    'add test_type_error_w_the_uncallables'
    

close the project

  • I close tests/test_type_error.py and src/type_error/__init__.py

  • I click in the terminal where the tests are running

  • I use q on the keyboard to leave the tests. The terminal goes back to the command line.

  • I change directory to the parent of type_error

    cd ..
    

    the terminal shows

    .../pumping_python
    

    I am back in the pumping_python directory.


review

The tests show that

All the tests so far show that I get TypeError when I call an object in a way that is different from its definition.

How many questions can you answer about TypeError with objects?


code from the chapter

Do you want to see all the CODE I typed in this chapter?


what is next?

Would you like to see another way to write tests?


rate pumping python

If this has been a 7 star experience for you, please CLICK HERE to leave a 5 star review of pumping python. It helps other people get into the book too.