skip to Main Content

I have a requirement to sort the data and below is what my data looks like.

[
  {
    "id": "course1",
    "type": "course",
    "sequence": 1
  },
  {
    "id": "course2",
    "type": "course",
    "sequence": 2
  },
  {
    "id": "course1_chapter1",
    "type": "chapter",
    "sequence": 1,
    "course": {
      "id": "course1",
      "sequence": 1
    }
  },
  {
    "id": "course1_chapter2",
    "type": "chapter",
    "sequence": 2,
    "course": {
      "id": "course1",
      "sequence": 1
    }
  },
  {
    "id": "course2_chapter1",
    "type": "chapter",
    "sequence": 1,
    "course": {
      "id": "course1",
      "sequence": 2
    }
  },
  {
    "id": "course1_chapter1_lesson1",
    "type": "lesson",
    "sequence": 1,
    "course": {
      "id": "course1",
      "sequence": 1
    },
    "chapter": {
      "id": "chapter1",
      "sequence": 1
    }
  },
  {
    "id": "course1_chapter1_lesson2",
    "type": "lesson",
    "sequence": 2,
    "course": {
      "id": "course1",
      "sequence": 1
    },
    "chapter": {
      "id": "chapter1",
      "sequence": 1
    }
  },
  {
    "id": "course1_chapter2_lesson1",
    "type": "lesson",
    "sequence": 1,
    "course": {
      "id": "course1",
      "sequence": 1
    },
    "chapter": {
      "id": "chapter1",
      "sequence": 2
    }
  }
]

Now my requirement is to sort the data based on type 1st where the order should be course, chapter, and lesson, and then order based on the sequence. So my final outcome expectation is as per the above data

course1, course2, course1_chapter1, course1_chapter2, course2_chapter1, course1_chapter1_lesson1, course1_chapter1_lesson2, course1_chapter1_lesson2, course1_chapter2_lesson1

The sample data which I have mentioned is already in sorted manner but in real time scenario, I get unsorted data.

right now I have sorted just by Type using the score.
I could do the sorting by splitting the data into different variable and finally get the sorted data into single variable but would like to know if there is any advance option which I might not be aware.

3

Answers


  1. The sort function takes as argument a comparison function that must return a negative value if its first argument is less than its second, a positive value if its first argument is greater than its second, and zero if they are equal.

    You can use this technique in your case by comparing the significance of types (course is more significant than chapter) and by comparing the sequence numbers within a given type:

    const types = ["course", "chapter", "lesson"];
    data.sort(function(a, b) {
      if (a.type !== b.type) return types.indexOf(a.type) - types.indexOf(b.type);
      for (var t of types) {
        if (t === a.type) return a.sequence - b.sequence;
        var d = a[t].sequence - b[t].sequence;
        if (d !== 0) return d;
      }
    });
    
    Login or Signup to reply.
  2. Maybe this will help you

    var array = [
    
        {
            "id": "course2",
            "type": "course",
            "sequence": 2
        },
        {
            "id": "course1_chapter1",
            "type": "chapter",
            "sequence": 1,
            "course": {
                "id": "course1",
                "sequence": 1
            }
        },
    
        {
            "id": "course1_chapter2",
            "type": "chapter",
            "sequence": 2,
            "course": {
                "id": "course1",
                "sequence": 1
            }
        },
        {
            "id": "course1",
            "type": "course",
            "sequence": 1
        },
        {
            "id": "course1_chapter1_lesson2",
            "type": "lesson",
            "sequence": 2,
            "course": {
                "id": "course1",
                "sequence": 1
            },
            "chapter": {
                "id": "chapter1",
                "sequence": 1
            }
        },
        {
            "id": "course2_chapter1",
            "type": "chapter",
            "sequence": 1,
            "course": {
                "id": "course1",
                "sequence": 2
            }
        },
        {
            "id": "course1_chapter1_lesson1",
            "type": "lesson",
            "sequence": 1,
            "course": {
                "id": "course1",
                "sequence": 1
            },
            "chapter": {
                "id": "chapter1",
                "sequence": 1
            }
        },
    
        {
            "id": "course1_chapter2_lesson1",
            "type": "lesson",
            "sequence": 1,
            "course": {
                "id": "course1",
                "sequence": 1
            },
            "chapter": {
                "id": "chapter1",
                "sequence": 2
            }
        }
    ]
    
    console.log("Original Array: ", array);
    
    array.sort(function (a, b) {
        if (a.type !== b.type) {
            if (a.type === "course") return -1;
            if (b.type === "course") return 1;
            if (a.type === "chapter") return -1;
            if (b.type === "chapter") return 1;
        }
        if (a.sequence > b.sequence) return 1;
    
        return -1;
    });
    
    console.log("Ordered Array: ", array);

    Be careful with sort function because it is mutable (you will lose original array)

    Login or Signup to reply.
  3. You can use a single expression in your sort callback:

    const data = [{"id": "course1","type": "course","sequence": 1},{"id": "course2","type": "course","sequence": 2},{"id": "course1_chapter1","type": "chapter","sequence": 1,"course": {"id": "course1","sequence": 1}},{"id": "course1_chapter2","type": "chapter","sequence": 2,"course": {"id": "course1","sequence": 1}},{"id": "course2_chapter1","type": "chapter","sequence": 1,"course": {"id": "course1","sequence": 2}},{"id": "course1_chapter1_lesson1","type": "lesson","sequence": 1,"course": {"id": "course1","sequence": 1},"chapter": {"id": "chapter1","sequence": 1}},{"id": "course1_chapter1_lesson2","type": "lesson","sequence": 2,"course": {"id": "course1","sequence": 1},"chapter": {"id": "chapter1","sequence": 1}},{"id": "course1_chapter2_lesson1","type": "lesson","sequence": 1,"course": {"id": "course1","sequence": 1},"chapter": {"id": "chapter1","sequence": 2}}];
    
    const result = data.sort((a, b) =>
        !b.course - !a.course || !b.chapter - !a.chapter
        || a.course?.sequence  - b.course?.sequence 
        || a.chapter?.sequence - b.chapter?.sequence 
        || a.sequence - b.sequence
    ).map(a => a.id);
    
    console.log(result);

    The first line of the expression checks if both items have a different granularity (for example, one has a chapter, the other doesn’t). If this condition is true, then precedence is given to the item that has least granularity.

    If that condition is false (i.e. they have the same granularity), then the available sequences are compared.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search