To prevent the need for redundant iterations, arrange an object based on a specific field

Looking for a way to avoid repeating the same loop multiple times while sorting an object efficiently.

Take a look at this sample object:

movies = [
    { 
        title: "The Lord of the Rings: The Fellowship of the Ring"
        year: 2001
    }, 
    { 
        title: "The Lord of the Rings: The Two Towers"
        year: 2002
    },
    { 
        title: "The Lord of the Rings: The Return of the King"
        year: 2003
    },
    { 
        title: "A Beautiful Mind"
        year: 2001
    },
]

The goal is to sort these movies by year and display them on the screen as follows:

Year 2003
- The Lord of the Rings: The Return of the King

Year 2002
- The Lord of the Rings: The Two Towers

Year 2001
- A Beautiful Mind
- The Lord of the Rings: The Fellowship of the Ring

To achieve this in vue, one could define an array years = [2003, 2002, 2001] and implement:

<div v-for="y in years">
    {{ y }}
    <div v-for="m in movies">
        <div v-if="m.year == y">
            {{ m.title }}
        </div>
    </div>
</div>

However, this method involves looping through movies for each element in the years array.

An alternative approach would be to restructure the movies object like this:

moviesByYear = [
    2003: [
        { 
            title: "The Lord of the Rings: The Return of the King"
            year: 2003
        }
    ], 
    2002: [
        {
            title: "The Lord of the Rings: The Two Towers"
            year: 2002    
        }
    ],
    2001: [
        {
            title: "A Beautiful Mind"
            year: 2001
        },
        {
            title: "The Lord of the Rings: The Fellowship of the Ring"
            year: 2001
        }
    ]
]

This structure allows for a more efficient implementation using:

<div v-for="(movies, year) in moviesByYear" :key="year">
    <div>{{ year }}</div>
    <div v-for="m in movies">>
        {{ m.title }}
    </div>
</div>

However, building the moviesByYear array poses challenges, especially if sorting by ascending and descending year is required.

Seeking advice on solving this issue. Is there a better solution than repetitive v-for loops?

Answer №1

It is possible that I am misunderstanding, but the initial step involves creating an array of objects that represent the relationship between years and movies. To reverse the order (ascending), you can simply reverse the array. This allows for easy iteration using a straightforward v-for loop, such as:

<div v-for="year in movieList" >
  <div>{{ year.year }}</div>
  <div v-for="m in year.movies">
    {{ m }}
  </div>
</div>

let films = [{
    title: "Inception",
    year: 2010
  },
  {
    title: "The Dark Knight",
    year: 2008
  },
  {
    title: "Interstellar",
    year: 2014
  },
  {
    title: "Dunkirk",
    year: 2017
  },
]

let movieList = films.reduce((b, a) => {
  let index = b.findIndex(f => f.year === a.year);
  if (index < 0) b.push({
    year: a.year,
    movies: [a.title]
  });
  else b[index].movies.push(a.title);
  return b;
}, []).sort((a, b) => b.year - a.year);

console.log(movieList)
console.log('reversed: ', movieList.reverse())

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Nuxt Authentication with Dual Local Endpoints

I am interested in creating two local endpoints like the ones below: strategies: { localOne: { endpoints: { login: { url: "token/", method: "post", propertyName: "access" }, user: { url: "user/me/", method: "get", propertyName: false }, ...

Generate a link that can easily be shared after the content has loaded using

One feature on my website involves a content container that displays different information based on which list item is clicked (such as news, videos, blogs, etc.). This functionality is achieved by using jQuery's load method to bring in html snippets ...

Fixing Timezone Issue in VueJs 3 with Axios POST Request

Having an issue with axios. In my application, I have an input field for datetime-local. When I select a date and time, the displayed time is correct (e.g., selecting 10:00 shows as 10:00), but when calling a function using axios.post, the request sends th ...

Encountering a TypeScript error in Vue 3 when trying to assign a type of '($event: any) => void' to an event listener

Snippet of component code: <h2 @click="handleEvent(post.id)">{{ post.title }}</h2> function handleEvent(id: number) { router.push("/post/" + id); } Error message in TypeScript: Type '($event: any) => void' i ...

Utilizing X-editable in an ASP MVC View: navigating the form POST action to the controller

I have been utilizing the X-Editable Plugin to collect user input and perform server submissions. However, I am encountering an error during submission. What adjustments should I make in order to ensure that the x-editable data functions properly with the ...

What is the best way to retrieve all dates that are older than 30 days using JavaScript?

I have the following code snippet as a reference and I'm attempting to retrieve a list of dates from 30 days before. What do I need to change? Date.prototype.addDays = function(days) { var newDate = new Date(this.valueOf()) newDate.s ...

Is there an issue with .addClass not working on imported HTML from .load in jQuery?

I have set up a navigation bar that hides when the user scrolls down and reappears when they scroll up. I want to keep the navbar code in a separate HTML file for easier editing. .load In the index.html file, the navbar code is included like this: <di ...

The NodeJS server experiences a crash immediately after attempting to save data into the MongoDB database

I have encountered an issue with a script that saves objects to a MongoDB database using mongoose. The object is successfully saved to the database, but immediately after, the server crashes and throws the error message: catch(err) { process.nextTick(funct ...

The callback function within the Service does not execute just once when utilizing $timeout

Looking to implement a service that functions similarly to this example. Here is the code I have so far: app.service('Poller', function ($q, $http, $timeout) { var notification = {}; notification.poll = function (callback, error) { return $ ...

Vue encountered an invalid value for the dynamic directive argument, which was expected to be a string or null, but

Hello, I am trying to use a dynamic argument for a directive in my HTML code: <div id="app5"> <p>{{message}}</p> <button v-on:[eventName]="reverseMessage">Reverse Message</button> </div> Here is my Vue instance ...

Refresh a row in real-time by utilizing a modal with JavaScript or jQuery

Is there a way to dynamically edit and update a previously submitted row (category name) in a table? I am able to edit a row by clicking on an edit button and displaying a modal with the current value. However, I am facing a challenge when trying to submit ...

Uploading CSV file in Angular to populate the scope rather than sending it to the server

I need assistance with allowing users to upload a CSV file, which will then be displayed and validated. Rather than uploading the file directly to the server, I would prefer to keep it within scope until validation is complete. Unfortunately, Angular 1.5. ...

I am unable to generate a vite application within WSL

My system is running node version 10.19.0 and npm version 6.14.4. Whenever I try to run create-vite@latest client, I encounter the following error: npx: installed 1 in 0.79s /home/victor/.npm/_npx/86414/lib/node_modules/create-vite/index.js:3 import &apos ...

Lack of animation on the button

Having trouble with this issue for 48 hours straight. Every time I attempt to click a button in the top bar, there is no animation. The intended behavior is for the width to increase and the left border color to change to green, but that's not what&ap ...

Tips on avoiding the accumulation of event handlers when dealing with click events triggered by the document selector in jQuery

I am currently working on a project that involves using AJAX to load various pieces of HTML code. This is done in order to properly position dynamic buttons within each portion of the HTML content. In my case, I need to trigger click events on the document ...

Generating numerous checkboxes dynamically

Seeking assistance with a jQuery function that dynamically generates or clones checkboxes. The challenge is to display the sub_item checkbox when the main_item checkbox is checked. For a demonstration, you can visit this DEMO Jquery $('#btnAdd' ...

The Node.js JSON string displays as "[object Object]" in the output

Front End // js / jquery var content = { info : 'this is info', extra : 'more info' } $.ajax({ type: 'POST', url: '/tosave', data: content }); Node // app.js app.post('/tosave', funct ...

Error with Cross-Origin Resource Sharing (CORS) upon inserting a parameter within an Express application

I'm completely stumped as to why this isn't functioning properly. My express app is deployed on Heroku and here's the code: var urlMetadata = require('url-metadata') var express = require('express') var cors = require( ...

jinja2.exceptions.UndefinedError: The variable 'participant' has not been defined

I am currently in the process of developing a video chat web application using Twilio, and I have been following a tutorial on how to build the application: . However, I keep encountering an error mentioned in the title. It seems like I am trying to access ...

Validation of dynamically generated name fields using radio button group

CODE: html <form id="myform" type="post"> <fieldset id="myid1"> <input id="entries_8490_burn_id_1" name="entries[8490][burn_id]" value="1" type="radio"/> <input id="entries_8490_burn_id_2" name="entries[8490][burn ...