7

Consider that I have a dictionary that looks like this:

{1=>a, 2=>b, 3=>c, 4=>d}

and a list that looks like this:

[1, 2, 3]

is there a method that'd return me a subdictionary only containing

{1=>a, 2=>b, 3=>c}

kjanko
  • 552
  • 1
  • 5
  • 24

1 Answers1

18

a regular dict-comprehension would do that:

d = {1: 'a', 2: 'b', 3: 'c', 4: 'd'}
keys = [1, 2, 3]

dct = {key: d[key] for key in keys}
print(dct)  # {1: 'a', 2: 'b', 3: 'c'}

there are 2 ways to handle keys in keys that are not in the original dictionary:

keys = [1, 2, 3, 7]

# default value None
dct = {key: d[key] if key in d else None for key in keys}
print(dct)  # {1: 'a', 2: 'b', 3: 'c', 7: None}

# ignore the key if it is not in the original dict
dct = {key: d[key] for key in set(keys).intersection(d.keys())}
print(dct)  # {1: 'a', 2: 'b', 3: 'c'}
hiro protagonist
  • 44,693
  • 14
  • 86
  • 111
  • Works fine. Thanks. – kjanko Jun 20 '17 at 13:43
  • Time limit :) Would you mind quickly showing me what's the syntax to check if the key from the list actually exists? – kjanko Jun 20 '17 at 13:46
  • @kjanko added an update for that. – hiro protagonist Jun 20 '17 at 13:50
  • @hiroprotagonist Thank you very much for your reply. It helps me. Is there a way that when a key is not found, I neither give a default value 'None' or ignore but store in a list so that I can later notify the user of missing keys? I tried `dct = {key: d[key] if key in d else missing.append(key) for key in keys}` but this still gives dct with None values for missing keys. I also tried `dct = {key: d[key] if key in d else missing.append(key) for key in set(keys).intersection(d.keys())}`. But this gave me empty dict and also empty missing list. Could you please help me – Priya Mar 28 '22 at 14:40
  • @Priya you could create `dct` as described above and then get the missing keys with `missing_keys = set(d) - set(keys)`. – hiro protagonist Mar 28 '22 at 14:58
  • @hiroprotagonist Thanks! But that is not what I want. But I want to list only the missing keys from `keys` that are not found in `d`. Eg: `d = {1: 'a', 2: 'b', 3: 'c', 4: 'd'}` `keys = [1, 2, 7, 8, 9]`. I just want to log `[7,8,9]` and create dct only with found values i.e., `print(dct) # {1: 'a', 2: 'b'}` – Priya Mar 29 '22 at 07:39
  • 2
    @Priya that would be `set(keys) - set(d)` or - if you prefer a list: `[k for k in keys if k not in d]`. – hiro protagonist Mar 29 '22 at 07:44
  • @hiroprotagonist Hey, thanks! That works. But it gives me `{1: 'a', 2: 'b', 7: None, 8: None, 9: None}`. Can I just extract it as `{1: 'a', 2: 'b'}` – Priya Mar 29 '22 at 07:48
  • @Priya sorry, i don't think i really understand your problem. what is your input and what is your desired output? you might even post that as a question (or here in the comments). – hiro protagonist Mar 29 '22 at 08:09
  • @hiroprotagonist Yes. I am almost near to answer. So I will just continue here. Eg: `d = {1: 'a', 2: 'b', 3: 'c', 4: 'd'} keys = [1, 2, 7, 8, 9]` Output: `1. dct = {1: 'a', 2: 'b'} and 2. missing_keys = [7,8,9]`. With your suggestions above, I get output currently as `1. dct = {1: 'a', 2: 'b', 7: None, 8: None, 9: None}` and `2. missing_keys=[7,8,9]` – Priya Mar 29 '22 at 08:20
  • 1
    @Priya `dct = {key: d[key] for key in set(keys) & set(d)}` and `missing_keys = set(keys) - set(d)` works for me. – hiro protagonist Mar 29 '22 at 09:36
  • @hiroprotagonist Very very very thanks! This is what I was looking for. I also now got this with another way of creating one more sub-list with only keys found and then creating dict. but your answer seems so simple and much elegant. Mine was a round about. I will take your answer. Thanks a lot lot nd lot :) – Priya Mar 29 '22 at 09:45
  • no problem! happy to help. happy pythoning! – hiro protagonist Mar 29 '22 at 09:46