PJ Drop
PJ Drop

Reputation: 50

Catching different TypeErrors

I have a dictionary that has three different kinds of key-value pairs in it. The values are one of the three shapes: A dictionary, null, or an integer, e.g.:

dic = {"range" : {"val": 1, "size": 2},
       "length" : {"val": 5, "radius": 1},
       "power": null,
       "current": 5}

I am using a try-except block, with the dictionary value as default, and want to catch the TypeError for null and integer separately. For value null, it gives "TypeError: 'NoneType' object is not subscriptable" and for an integer, it gives "TypeError: 'int' object is not subscriptable". How do I catch these errors in different exceptions? I am looping through the keys of interest in the dictionary and an example of what I am currently doing is below, however it catches both errors as they are both TypeError:

for kw in list_of_keys:
    try:
        val_test = dic[kw]['val']
    except TypeError:
        val_test = dic[kw]

I would like to catch errors similar to the following:

for kw in list_of_keys:
    try:
        val_test = dic[kw]['val']
    except TypeError: 'int' object is not subscriptable:
        val_test = dic[kw]
    except TypeError: 'NoneType' object is not subscriptable:
        val_test = "Not implemented / Not given yet"

Thank you for your help!

Upvotes: 0

Views: 49

Answers (3)

Mahbubur Rahman
Mahbubur Rahman

Reputation: 361

You can use .get() to check None or boolen and isinstance method to check if it is an integer.

for kw in list_of_keys:

    val = dic.get(kw)
    
    if not val:
       val = "NoneType Error"
    
    elif isinstance(val,int):
       val = "Integer Error"
    
    else:
        val=val['val']

Upvotes: 0

chepner
chepner

Reputation: 530960

Exceptions are for, well, exceptional results. Here, a None or int value seems just as valid as a dict value, so you should just look at dic[kw] before assuming it is a dict.

for kw in list_of_keys:
    v = dic[kw]
    if v is None:
        val_test = "Not implemented / Not given yet"
    else:
        try:
            val_test = v['val']
        except TypeError:
            val_test = v

Once you've determined if v is None or not, then you can try to index it and assume it is an int on a TypeError.

Upvotes: 2

avats
avats

Reputation: 445

You can use type() keyword to check if a variable is Integer or NoneType and use try-except accordingly.

Otherwise to check if a variable is subscriptable:

from collections.abc import Iterable

if isinstance(theElement, Iterable):
    # iterable
else:
    # not iterable

You can also use hasattr(myObj, '__getitem__') to check this for objects with __getitem__ method such as dict.

Upvotes: 1

Related Questions