1

I have a dictionary with 6 keys and each key's value is a list with 100 elements

my_dict = {"Key1":["name1", "name2", ..., "name100"],
           "Key2":["id1", "id2", ..., "id100"],
            ...
           "Key6":["type1", "type2", ..., "type100"]}

I am trying to make a table that is 100 x 6, where each column will be a list. I have tried everything in the template and come up short every time. Is there some simple concept I am missing? Should I be manipulating the data in the backend to make it more manageable?

Edit: I probably should be more clear. I can render my template fine, I can put stuff in a table, just not how I want to.

I can do things like

<tr>
  {% for i in my_dict.items %} 
  <td>{{i}}</td>
  {% endfor %}
</tr>

Giving me 1 row with 6 columns

or

{% for items in dict.items %}
  <tr>
    {% for item in items %}
      <td>{{item}}</td>
    {% endfor %}
  </tr>
{% endfor %}

giving me 6 rows and 100 columns

I could do

{% for item in dict.Key1 %}
  <tr>
    <td>{{item}}</td>
  </tr>
{% endfor %}

Giving me 1 column and 100 rows

But I need each item, in each list, in its own column.

Nick Ruha
  • 45
  • 2
  • 7
  • There are 2D lists in python try to use them, But if you want to go for tables go for https://stackoverflow.com/questions/9535954/printing-lists-as-tabular-data may be this helps you – Sagar Feb 08 '18 at 21:22
  • you mean you can't render the dict as a table? if so update your question with the code you tried..please – mohammedgqudah Feb 08 '18 at 21:24

2 Answers2

2

If I am correct, your table needs to have 6 columns and 100 rows right? If so it is difficult to do that in the template, and I would edit the data before sending it to the template. Usually you should always try to keep complicated logic like that outside of the template anyways.

View:

def get_context_data(self, **kwargs):
    context = super(YOUR_CLASS_HERE, self).get_context_data(**kwargs)
    # I defined each list this way just to test
    my_dict = {
        "Key1": ["name1", "name2", "name100"],
        "Key2": ["id1", "id2", "id100"],
        "Key6": ["type1", "type2", "type100"]
    }
    my_data = [[v[i] for k, v in my_dict.items()] for i in range(3)]  # This would be range(100) for you, once again I was just testing.
    context['my_data'] = my_data
    return context

And in the template:

<table>
    <thead>
    </thead>
    <tbody>
        {% for row in my_data %}
            <tr>
            {% for entry in row %}
                <td>{{ entry }}</td>
            {% endfor %}
            </tr>
        {% endfor %}
    </tbody>
</table>

Edit: I believe this solution solves your problem in the best way. Granted it does the work in the view rather than the template, but you don't want to do this type of data manipulation in the template. This solution changes the data with 1 line of code:

my_data = [[v[i] for k, v in my_dict.items()] for i in range(100)]

It's much easier to do it in python than with the template tags in the template. I can't think of a way to do it in the template without writing a custom template tag. If you do use a custom template tag, then your still using python so you should have just done it in the view.

Nathan Smith
  • 133
  • 1
  • 7
  • This works perfectly and it's a one liner, thank you. It is disappointing that django doesn't have a method to do this. I can't work with a database for this project and not relying on an RDB is tricky. – Nick Ruha Feb 10 '18 at 02:48
0

May be you are asking for this (how to render this dict on template side). Try this,I hope, I got your question right as it is not clear much otherwise make me correct.

{% for key, value_list  in my_dict.items %}
  # your stuff 
  {% for value in value_list %}
    # more stuff here (2)
  {% endfor %}
{% endfor %}
Sagar
  • 1,115
  • 2
  • 11
  • 23
  • This will make a list turn into a row. I'll then end up with 6 rows and 100 columns. I did edit my question to be more concise, but thank you. – Nick Ruha Feb 09 '18 at 00:00