Empresas
Empleos
  • Sobre nosotros
  • Soluciones
    • Publicación de vacantes
      Publica tu vacante y recibe candidatos calificados en 48h.
    • Evaluación de candidatos
      500+ pruebas técnicas y psicológicas, más anti-fraude.
    • Headhunting
      Búsqueda ejecutiva a la medida de principio a fin.
    • Nómina + EOR
      Dispersión de nómina y EOR en más de 15 países de LATAM.
  • Precios
  • Empleos

0

149
Vistas
Svelte Performance: Derived from custom stores of arrays

I'm making a Trello clone in Svelte using custom and derived stores. Svelte reactivity watches for assignment, so I need to reassign my array stores, but I noticed stores derived from writeable arrays recalculate the entire array. Surely I can be more performant here, especially if only a single array value is updated?

// The store in question, edited for terseness
const cards = writeable([]);

// adding to the card somewhere in code
cards.update((cards) => (cards = [...cards, card]));

// the derived store, that loops through all cards (because of reduce)
// this groups the card by its listId
const cardsGroupedByList = derived(cards, ($cards) => {
  return $cards.reduce((list, card) => {
    console.log('recalculating cards');
    const data = list.get(card.listId) || [];
    return list.set(card.listId, [...data, card]);
  }, new Map());
});

In the console, cardsGroupedByList will print n times, but Svelte only renders the corresponding component once, so this is purely data manipulation. Is there a better way to do this?

Here's a working Svelte REPL with multiple lists and cards.

about 4 years ago · Juan Pablo Isaza
2 Respuestas
Responde la pregunta

0

One potential solution is to have 2 custom stores. It only updates once, but definitely loses the elegance of a derived store.

// cards now need their set and add methods modified
// otherwise I risk my group running out of sync
export const cards = (() => {
  const { subscribe, set, update } = writable<Card[]>([]);

  return {
    subscribe,
    set: (cards: Card[]) => {
      cardsGroupedByList.set(cards); // set the group, reduce once
      set(cards);
    },
    add: (card: Card) => {
      cardsGroupedByList.update(card); // add to the group
      update((cards) => (cards = [...cards, card]));
    },
  };
})();

// groupBy becomes a custom store that retains internal state
// run the risk of the group becoming out of sync with cards
// could have issues when the card moves -- would need to add/remove or recalc
export const cardsGroupedByList = (() => {
  const init = new Map();
  const { subscribe, set, update } = writable(init);

  function groupBy(groups, card) {
    console.log('calculating groups');  // same console log, only happens once
    const data = groups.get(card.listId) || [];
    return groups.set(card.listId, [...data, card]);
  }

  return {
    subscribe,
    set: (cards: Card[]) => set(cards.reduce(groupBy, init)),
    update: (card) => {
      update((groups) => groupBy(groups, card));
    },
  };
})();
about 4 years ago · Juan Pablo Isaza Denunciar

0

In your specific use case you dont need to create an additionnal store and you could simply reduce in the App script :)

App.svelte

<script>
  import { cards } from './card-store.js';
  import Card from './Card.svelte';
  import CardForm from './CardForm.svelte';
  let cardsList
  $: cardsList = $cards.reduce((acc, card) => {
    acc[card.listId] = acc[card.listId] || []
    acc[card.listId].push(card)
    return acc
  }, {})
</script>

{#each [1,2,3] as idx}
  <h2>List: {idx}</h2>
  <ul>
    {#each cardsList[idx] as card}
      <Card {...card} />
    {/each}
  </ul>
  <CardForm listId={idx} />
{/each}

And remove the cardsGroupedByList entry from the card-store

edit: Im not sure this is much different from what you do since the structure is recomputed each time anyway :/

about 4 years ago · Juan Pablo Isaza Denunciar
Responde la pregunta
Encuentra empleos remotos

¡Descubre la nueva forma de encontrar empleo!

Top de empleos
Top categorías de empleo
Empresas
Publicar vacante Precios Comercial
Legal
Términos y condiciones Política de privacidad
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomiéndame algunas ofertas
Necesito ayuda