Skip to content
Advertisement

Sort dict in jinja2 loop

I’m still learning jinja2 and flask and I’m having a difficulty using dictsort in jinja2.

So I’m passing this dict into a jinja2 template:

{'PEDD United': {'id': 37828, 'rank': 12, 'totalpts': 307},'Fc Mbonabushia': {'id': 205633, 'rank': 6, 'totalpts': 356},'FC Slurp': {'id': 933573, 'rank': 11, 'totalpts': 312},'KFC_Overijse': {'id': 38861, 'rank': 5, 'totalpts': 362},'Fc Paris': {'id': 1538051, 'rank': 2, 'totalpts': 396}}

What I want is create a table that is sorted by the value of the key ‘totalpts’. I tried all sort of things and it just doesn’t take totalpts into account when “sorting”.

Here’s one of my code:

        <table class="table table-bordered">
        {% for team in league %}
            <tr>
                <td>{{team}}</td>
                {% for data in league[team]|dictsort(league[team]['totalpts']) %}
                <td>{{ league[team]['totalpts'] }}</td>
                {% endfor %}
            </tr>
        {% endfor %}
    </table>

by it doesn’t sort anything in this case… Just print the value in the table without any order…

Anyone can help me out?

thanks

Advertisement

Answer

The way you’re doing this will not work, because as soon as you use {% for team in league %}, you’re already using the unsorted dict and extracting the key,value pair from it.

I think |dictsort may not be able to help you in this case because you cannot sort by either key or value, but by the value’s (sub-dict’s) value for ‘totalpts’.

Instead, you should sort this dictionary before passing it to the template, in the following way:

>>> from collections import OrderedDict
>>> league={'PEDD United': {'id': 37828, 'rank': 12, 'totalpts': 307},'Fc Mbonabushia': {'id': 205633, 'rank': 6, 'totalpts': 356},'FC Slurp': {'id': 933573, 'rank': 11, 'totalpts': 312},'KFC_Overijse': {'id': 38861, 'rank': 5, 'totalpts': 362},'Fc Paris': {'id': 1538051, 'rank': 2, 'totalpts': 396}}
>>> league = OrderedDict(sorted(league.items(), key= lambda x: x[1]['totalpts'], reverse=True))
>>> print league
OrderedDict([('Fc Paris', {'id': 1538051, 'rank': 2, 'totalpts': 396}), ('KFC_Overijse', {'id': 38861, 'rank': 5, 'totalpts': 362}), ('Fc Mbonabushia', {'id': 205633, 'rank': 6, 'totalpts': 356}), ('FC Slurp', {'id': 933573, 'rank': 11, 'totalpts': 312}), ('PEDD United', {'id': 37828, 'rank': 12, 'totalpts': 307})])

To sort the dict, we convert it into a list of tuples of (key ,value) using .items(). Assuming x is one such tuple, x[1] contains the dictionary with the ‘totalpts’ key.

>>> league.items()[0]
('Fc Paris', {'id': 1538051, 'rank': 2, 'totalpts': 396})  # = x

So now we sort the tuples usingx[1]['totalpts'], using reverse=True for a decreasing order.

A dict itself cannot be sorted, it is an unordered data type – You can either use an OrderedDict, or you can simply use tuples:

>>> sorted(league.items(), key= lambda x: x[1]['totalpts'], reverse=True)
[('Fc Paris', {'id': 1538051, 'rank': 2, 'totalpts': 396}), ('KFC_Overijse', {'id': 38861, 'rank': 5, 'totalpts': 362}), ('Fc Mbonabushia', {'id': 205633, 'rank': 6, 'totalpts': 356}), ('FC Slurp', {'id': 933573, 'rank': 11, 'totalpts': 312}), ('PEDD United', {'id': 37828, 'rank': 12, 'totalpts': 307})]
User contributions licensed under: CC BY-SA
2 People found this is helpful
Advertisement