Search code examples
djangodjango-admindjango-admin-filtersdjango-admin-tools

How can I sort and include rules sorting in django?


I'm not to confident that I am asking this question correctly but this is what I'd like to do.

In django admin, I would like to write an action that sorts the list of my contestants randomly and doesn't allow two people with the same first name to be within 4 records of eachother. So basically, if you have John L. John C. Carey J, Tracy M. Mary T., the records would be listed like this:

John L.

Mary T.

Carey J.

Tracy T.

John C.

              OR

How can I write an action that would create random groups where two people with the same name wouldn't be within the same group like so:

John L. John C. Carey J, Tracy M. Mary T. =

Group 1

John L.

Mary T.

Carey J.

Tracy T.

Group 2

John C.

Forgive me if it isn't very clear, let me know and I'll try to specify further but any help would be appreciated

EDIT: 
Is this what you are referring to? I can't quite figure out how to compare the fields to see if they are the same

   Model:
class people(models.Model)
   fname = model.CharField()
   lname = model.CharField()
   group = model.IntegerField()


 View:
   N = 4
   Num = randint(0, N-1)
   for x in queryset:
       x.group = Num
       if group == group| fname == fname | lname == lname:
           x.group = (Num + 1) % N

Solution

  • Your first question cannot be solved always. Just think of all contestants have the same name, then you actually cannot find a solution to it.

    For the second question, I can suggest an algorithm to do that, though. Since I do not see any restriction on the number of groups, I will suggest a method to create the least number of groups here.

    EDIT: I assumed you don't want 2 people with same "First name" in a group.

    The steps are

    1. Count the appearance of each name

      count = {}
      for x in queryset:
          if x.fname not in count:
               count[x.fname] = 0
          count[f.name] += 1
      
    2. Find the name with the most appearance

      N = 0
      for x in queryset:
          if count[x.fname] > N:
              N = count[x.fname]
      
    3. Create N groups, where N equals to the number of appearance of the name in step 2

    4. For each name, generate a random number X, where X < N.

      Try to put the name into group X. If group X has that name already, set X = (X + 1) % N and retry, repeat until success. You will always find a group to put the contestant.

      from random import randint
      groups = [[]] * N
      for item in queryset:
          X = randint(0, N-1)
          while item.fname in groups[X]:
              X = (X + 1) % N
          groups[X].append(item.fname)
          item.group = X
      

    EDIT:

    Added details in steps 1, 2, 4.

    From the code segment in your edited, I think you do not actually need a definition of "group" in model, as seems you only need a group number for it.