Search code examples
pythonfunctionloopsvariablesfor-in-loop

How to match data in two variables (list and dict) and print output combined


I have two variables:

documents = [
    {'type': 'passport', 'number': '2207 876234', 'name': 'Smith'},
    {'type': 'invoice', 'number': '11-2', 'name': 'Obama'}, 
    {'type': 'insurance', 'number': '10006', 'name': 'Carpenter'}
]
directories = {'1': ['2207_876234', '11-2'], '2': ['10006'], '3': ['0']}

I have to write a code to have output in the format: №: 2207 876234, type: passport, owner: Smith, shelf number: 1 №: 11-2, type: invoice, owner: Obama, shelf number: 1 №: 10006, type: insurance, owner: Carpenter, shelf number: 2

So I have written a code to start with

for k, v in directories.items():
    for info in documents:
        if v in [info]:
            print(k([info['number']]))

This seems not correct. Can somebody with experience give me an idea of how to combine two variables in one output format.


Solution

  • This isn't the prettiest but it works.

    documents = [
        {'type': 'passport', 'number': '2207 876234', 'name': 'Smith'},
        {'type': 'invoice', 'number': '11-2', 'name': 'Obama'}, 
        {'type': 'insurance', 'number': '10006', 'name': 'Carpenter'}
    ]
    directories = {'1': ['2207_876234', '11-2'], '2': ['10006'], '3': ['0']}
    
    entry_count = 0
    out = []
    for j,k in enumerate(directories):
        v = directories[k]
        for i,n in enumerate(directories[k]):
            if n == '0': 
                break
            data = documents[entry_count]
            out.append({ 'No': n, 'type': data['type'], 'owner': data['name'], 'shelf number': j + 1 })
            entry_count += 1
    
    print(out)
    

    Output:

    [{'no': '2207_876234', 'type': 'passport', 'owner': 'Smith', 'shelf number': 1},
     {'no': '11-2', 'type': 'invoice', 'owner': 'Obama', 'shelf number': 1},
     {'no': '10006', 'type': 'insurance', 'owner': 'Carpenter', 'shelf number': 2}]
    

    After some thought on this it occurred to me that although your documents and directories have their number values in the same order in the example data, the above method would not hold up if their order changed.

    However, the first value in directories['1'] does not match the first number in documents - '2207 876234' =/= '2207_876234'

    If we change the number in documents to match that in directories, the following code works and although slower, makes sure the number values match up regardless of the order the objects are in:

    documents = [
        {'type': 'passport', 'number': '2207_876234', 'name': 'Smith'},
        {'type': 'invoice', 'number': '11-2', 'name': 'Obama'}, 
        {'type': 'insurance', 'number': '10006', 'name': 'Carpenter'}
    ]
    directories = {'1': ['2207_876234', '11-2'], '2': ['10006'], '3': ['0']}
    
    out = []
    for j,k in enumerate(directories):
        v = directories[k]
        for i,n in enumerate(directories[k]):
            data = next((d for d in documents if n == d['number']), None)
            if not data:
                continue
            out.append({ 'No': n, 'type': data['type'], 'owner': data['name'], 'shelf number': j + 1 })
    
    print(out)
    

    Output:

    [{'No': '2207_876234', 'type': 'passport', 'owner': 'Smith', 'shelf number': 1},
     {'No': '11-2', 'type': 'invoice', 'owner': 'Obama', 'shelf number': 1},
     {'No': '10006', 'type': 'insurance', 'owner': 'Carpenter', 'shelf number': 2}]
    

    Note that the outputs are identical but the first method will not work if documents is re-ordered.