No me gusta usar mapas y bucles para crear una nueva matriz a partir de una matriz anterior en JavaScript cuando solo cambia un elemento. Tengo una matriz simple que tiene datos como este:

const speakerData = [{name: 'joe',id: 101,favorite: true}, {name: 'sam',id: 102,favorite: false}, {name: 'jon',id: 103,favorite: false}] 

Y quiero actualizar el registro 102 a favorito es verdadero (alternar favorito).

Tengo el siguiente código que funciona:

 const speakerId = 102; const newSpeakerData = speakerData.map((rec) ={amp}gt; { if (rec.id === speakerId) { rec.favorite = !rec.favorite; return rec; } else { return rec; } }); 

Quiero algo como lo que tengo a continuación, pero obviamente no funciona.

 const speakerRec = speakerData.find(a={amp}gt;a.id === speakerId); speakerRec.favorite = !speakerRec.favorite; const newSpeakerData = [{...speakerData},speakerRec] 

¿Hay una línea inteligente que pueda hacer que esto suceda con ES7?

Una opción es, durante el mapeo, también poner favorite: id === speakerId ? !favorite : favorite favorite: id === speakerId ? !favorite : favorite en el objeto devuelto:

 const speakerData = [{ name: 'joe', id: 101, favorite: true }, { name: 'sam', id: 102, favorite: false }, { name: 'jon', id: 103, favorite: false } ]; const speakerId = 102; const mappedData = speakerData.map(({ favorite, name, id }) ={amp}gt; ({ name, id, favorite: id === speakerId ? !favorite : favorite })); console.log(mappedData); 

No parece tan bonito, pero eso es lo que preferiría, y dudo que haya una mejor manera.

O bien, puede aplastarlo en una línea si realmente tiene que hacerlo (pero probablemente no debería, es demasiado difícil de leer):

 const mappedData = speakerData.map(({ favorite, name, id }) ={amp}gt; ({ name, id, favorite: id === speakerId ? !favorite : favorite })); 

Necesita bastante el map para mantener la matriz inmutable, pero puede salirse con una sintaxis más ordenada utilizando el operador condicional en lugar de las instrucciones if / else :

 const speakerId = 102; const newSpeakerData = speakerData.map((rec) ={amp}gt; rec.id === speakerId ? {...rec, favorite: !rec.favorite} : rec ); 

(El uso de sintaxis extendida también se asegura de no mutar el objeto rec ).

Si todavía es demasiado largo o tiene demasiada sangría, por supuesto, puede escribir una función auxiliar para usar como

 const matchSpeakerId = rec ={amp}gt; rec.id === 102; const newSpeakerData = mapWhere(speakerData, matchSpeakerId, rec ={amp}gt; ({...rec, favorite: !rec.favorite}));