I am having a dictionary that I would like to retrieve some values from using .get() method and if the key is not present, a default function should be executed that returns the correct value but it should only be executed if the key is not present.
I tried removing the default value and it works, so why does the function gets executed even if it won't be used?
The SQL query will return nothing because it only contains values not already in the dict
def get_port():
def default():
cursor.execute("SELECT port FROM table WHERE server=%s LIMIT 1",(server_name,))
return cursor.fetchone()[0]
port = {
'server1': 2222,
'server2': 2223,
'server3': 2224
}
#print(port.get(server_name)) << Works
return port.get(server_name, default())
Error:
return cursor.fetchone()[0] TypeError: 'NoneType' object is not subscriptable
I expect the default function to only execute if key is not present..
the issue with get
with a default value which needs build/evaluation is that the code is executed, even if not needed, which can slow down the code, or in your case trigger unnecessary errors.
An alternative could be:
port.get(server_name) or default()
If get
returns None
because a key is not found, then or default()
is activated. But if get
returns something, it short-circuits and default()
is not called.
(this could fail if get
returned empty string, zero, any "falsy" value but in your case - a server name - I'll suppose that it cannot happen)
Another option (maybe overkill here) would be to use a collections.defaultdict
object
port = collections.defaultdict(default)
port.update({
'server1': 2222,
'server2': 2223,
'server3': 2224
})
Then each call to port[server]
with an unknown key calls the default
function and stores the result in the dictionary. Make port
global or persistent and you have a created nice cache: next time the same value is fetched the default is already in the dictionary.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With