660

I am trying to check if a dictionary is empty but it doesn't behave properly. It just skips it and displays ONLINE without anything aside from the display the message. Any ideas why ?

def isEmpty(self, dictionary):
    for element in dictionary:
        if element:
            return True
        return False

def onMessage(self, socket, message):
    if self.isEmpty(self.users) == False:
        socket.send("Nobody is online, please use REGISTER command" \
                 " in order to register into the server")
    else:
        socket.send("ONLINE " + ' ' .join(self.users.keys()))    
Gino Mempin
  • 25,369
  • 29
  • 96
  • 135
Unsparing
  • 6,985
  • 2
  • 17
  • 33
  • 8
    To check if `self.users` is nonempty, just do `if self.users`. – BrenBarn Apr 20 '14 at 01:31
  • 4
    Your `isEmpty` actually returns `True` if the first key yielded from the dictionary is truey and returns `False` otherwise. If the dictionary is empty, it returns `None` which is not `== False`. – Hyperboreus Apr 20 '14 at 02:08
  • Your if statement is backwards. – Mad Physicist Apr 21 '15 at 03:55
  • be careful to false-like keys http://stackoverflow.com/a/17347421/1379762 – Wajih Feb 06 '16 at 19:20
  • Possible duplicate of [Python:Efficient way to check if dictionary is empty or not](http://stackoverflow.com/questions/13312043/pythonefficient-way-to-check-if-dictionary-is-empty-or-not) – tripleee Apr 21 '16 at 06:12
  • uhhh, `.join(...)` meaning `socket.join(...)`? Is that legal syntax? If so I'd rather like to avoid it, but still interested to know more if there's documentation on it particularly. duhhh, nevermind... string join :D – Nolo Sep 28 '20 at 09:38

8 Answers8

1149

Empty dictionaries evaluate to False in Python:

>>> dct = {}
>>> bool(dct)
False
>>> not dct
True
>>>

Thus, your isEmpty function is unnecessary. All you need to do is:

def onMessage(self, socket, message):
    if not self.users:
        socket.send("Nobody is online, please use REGISTER command" \
                    " in order to register into the server")
    else:
        socket.send("ONLINE " + ' ' .join(self.users.keys()))
218

Here are three ways you can check if dict is empty. I prefer using the first way only though. The other two ways are way too wordy.

test_dict = {}

if not test_dict:
    print "Dict is Empty"


if not bool(test_dict):
    print "Dict is Empty"


if len(test_dict) == 0:
    print "Dict is Empty"
doubleo
  • 4,389
  • 4
  • 16
  • 19
  • 99
    Sigh ... everybody likes to be "pythonic" and goes for the least characters to type. First, another criteria is readability. Second, the first test in the answer above is true not only if the dict exists and is empty, but also if test_dict is None. So use this test only when you know that the dict object exists (or when the difference does not matter). The second way also has that behavior. Only the third way barks if test_dict is None. – Andreas Maier Dec 12 '16 at 19:37
  • 1
    @AndreasMaier Exactly my feeling as well. Also, python is dynamically typed. Inside a function it's common to check "if x is non-empty dictionary, then do this; if x is non-empty numpy array, then do that". Then the first code will fail on `if x` when x is numpy array – jf328 Dec 15 '16 at 08:36
  • 1
    @Wajih you link is still irrelevant here... See [why](http://stackoverflow.com/questions/23177439/python-checking-if-a-dictionary-is-empty-doesnt-seem-to-work#comment-71768805) – Ulysse BN Feb 17 '17 at 20:44
  • 3
    Not upvoting this although technically correct due to concerns I share with. @AndreasMaier – Stunner Dec 17 '18 at 23:36
34
d = {}
print(len(d.keys()))

If the length is zero, it means that the dict is empty.

Gino Mempin
  • 25,369
  • 29
  • 96
  • 135
Achilles Ram Nakirekanti
  • 3,623
  • 1
  • 21
  • 13
  • 4
    While this code snippet may solve the question, [including an explanation](http://meta.stackexchange.com/questions/114762/explaining-entirely-code-based-answers) really helps to improve the quality of your post. Remember that you are answering the question for readers in the future, and those people might not know the reasons for your code suggestion. – DimaSan Dec 16 '16 at 11:43
  • 6
    `len(dict.keys())` is equivalent to `len(dict)` – pdpAxis Jun 04 '20 at 18:45
  • @pdpAxis In the value it gives, though I bet the implementation of `dict.__len__` is probably a bit faster. :) – Mateen Ulhaq Jun 11 '20 at 02:21
24

Simple ways to check an empty dict are below:

a = {}
  1. if a == {}:
      print ('empty dict')
    
  2. if not a:
      print ('empty dict')
    

Method 1 is more strict, because when a = None, method 1 will provide the correct result, but method 2 will give an incorrect result.

Gino Mempin
  • 25,369
  • 29
  • 96
  • 135
Shagun Pruthi
  • 1,813
  • 15
  • 19
9

A dictionary can be automatically cast to boolean which evaluates to False for empty dictionary and True for non-empty dictionary.

if myDictionary: non_empty_clause()
else: empty_clause()

If this looks too idiomatic, you can also test len(myDictionary) for zero, or set(myDictionary.keys()) for an empty set, or simply test for equality with {}.

The isEmpty function is not only unnecessary but also your implementation has multiple issues that I can spot prima-facie.

  1. The return False statement is indented one level too deep. It should be outside the for loop and at the same level as the for statement. As a result, your code will process only one, arbitrarily selected key, if a key exists. If a key does not exist, the function will return None, which will be cast to boolean False. Ouch! All the empty dictionaries will be classified as false-nagatives.
  2. If the dictionary is not empty, then the code will process only one key and return its value cast to boolean. You cannot even assume that the same key is evaluated each time you call it. So there will be false positives.
  3. Let us say you correct the indentation of the return False statement and bring it outside the for loop. Then what you get is the boolean OR of all the keys, or False if the dictionary empty. Still you will have false positives and false negatives. Do the correction and test against the following dictionary for an evidence.

myDictionary={0:'zero', '':'Empty string', None:'None value', False:'Boolean False value', ():'Empty tuple'}

Della
  • 1,264
  • 2
  • 15
  • 32
5

1st Way

len(given_dic_obj) 

It returns 0 if there are no elements. Else, returns the size of the dictionary.

2nd Way

bool(given_dic_object)

Returns False if the dictionary is empty, else return True.

Gino Mempin
  • 25,369
  • 29
  • 96
  • 135
Arpan Saini
  • 4,623
  • 1
  • 42
  • 50
0

You can also use get(). Initially I believed it to only check if key existed.

>>> d = { 'a':1, 'b':2, 'c':{}}
>>> bool(d.get('c'))
False
>>> d['c']['e']=1
>>> bool(d.get('c'))
True

What I like with get is that it does not trigger an exception, so it makes it easy to traverse large structures.

MortenB
  • 2,749
  • 1
  • 31
  • 35
-8

use 'any'

dict = {}

if any(dict) :

     # true
     # dictionary is not empty 

else :

     # false 
     # dictionary is empty
henrycarteruk
  • 12,708
  • 2
  • 36
  • 40
chhotu sardar
  • 63
  • 1
  • 1
  • 4
    `any` checks if the dict contains any truthy key, e.g. `any({0: 'something'})` returns `False` even though the dict is not empty – Railslide May 13 '16 at 12:52
  • yeah that to save from both cases , truthy and blank, other wise bool would have given true for truthy case . if you think in general coding purpose . – chhotu sardar May 14 '16 at 17:29