Combine dos matrices después de usar el método de filtro

9

Estoy atascado mostrando la página del carrito donde se enumeran los productos que los usuarios agregaron al carrito. Tengo dos matrices: una con los detalles del producto.

productDetails: [
            {
              productID: 1,
              productTitle: 'Product Title 1',
              productPrice: 2000
            },
            {
              productID: 2,
              productTitle: 'Product Title 2',
              productPrice: 5000
            },
            {
              productID: 3,
              productTitle: 'Product Title 3',
              productPrice: 1000
            },
            {
              productID: 4,
              productTitle: 'Product Title 4',
              productPrice: 10000
            }
          ],

Otro con detalles del producto del carrito que tiene la identificación del producto y la cantidad seleccionada solo por los usuarios.

cartProducts: [
            {
              productID: 1,
              quantity: 5,
            },
            {
              productID: 3,
              quantity: 2,
            }
          ]

He filtrado todos los productos que el usuario ha seleccionado.

cartItemDetails() {
      return this.productDetails.filter(
        el => this.cartProducts.some(f => f.id === el.productID),
      );
    },

Esta función proporciona los detalles del producto de productID 1 y 3. Lo que quiero es una nueva matriz que agregue el atributo de cantidad de cartProducts array a productDetails.

newArray: [
            {
              productID: 1,
              productTitle: 'Product Title 1',
              productPrice: 2000,
              quantity:5
            },
            {
              productID: 3,
              productTitle: 'Product Title 3',
              productPrice: 1000,
              quantity:5
            }
          ]

Espero haber aclarado mis preguntas. También estoy tratando de resolver este problema con el método map javascript pero no funciona.

Saludos,

Sujan Shrestha
fuente

Respuestas:

3

Puede usar map () después filter()y agregar quantitypropiedades a cada elemento.

const productDetails = [{ productID: 1, productTitle: 'Product Title 1', productPrice: 2000 }, { productID: 2, productTitle: 'Product Title 2', productPrice: 5000 }, { productID: 3, productTitle: 'Product Title 3', productPrice: 1000 }, { productID: 4, productTitle: 'Product Title 4', productPrice: 10000 }];
const cartProducts = [{ productID: 1, quantity: 5 }, { productID: 3, quantity: 2 }]; 

function cartItemDetails() {
  return productDetails
    .filter(el => cartProducts.some(f => f.productID === el.productID))
    .map(item => ({
      ...item,
      "quantity": cartProducts.find(f => f.productID === item.productID).quantity
    }));
}

console.log(cartItemDetails());

O puede usar reduce () .

const productDetails = [{ productID: 1, productTitle: 'Product Title 1', productPrice: 2000 }, { productID: 2, productTitle: 'Product Title 2', productPrice: 5000 }, { productID: 3, productTitle: 'Product Title 3', productPrice: 1000 }, { productID: 4, productTitle: 'Product Title 4', productPrice: 10000 }];
const cartProducts = [{ productID: 1, quantity: 5 }, { productID: 3, quantity: 2 }]; 

function cartItemDetails() {
  return productDetails.reduce((acc, curr) => {
    let item = cartProducts.find(f => f.productID === curr.productID);

    if (item) {
      acc.push({ ...curr,
        "quantity": item.quantity
      });
    }

    return acc;
  }, []);
}

console.log(cartItemDetails());

También puedes usar map()en cartProducts.

const productDetails = [{ productID: 1, productTitle: 'Product Title 1', productPrice: 2000 }, { productID: 2, productTitle: 'Product Title 2', productPrice: 5000 }, { productID: 3, productTitle: 'Product Title 3', productPrice: 1000 }, { productID: 4, productTitle: 'Product Title 4', productPrice: 10000 }];
const cartProducts = [{ productID: 1, quantity: 5 }, { productID: 3, quantity: 2 }]; 

function cartItemDetails() {
  return cartProducts.map(item => ({
    ...productDetails.find(f => f.productID === item.productID),
    ...item
  }));
}

console.log(cartItemDetails());

Nikhil
fuente
Muy apreciado. Gracias por diferentes variedades de respuestas. Estoy aceptando esta respuesta entre otras debido a su variedad de métodos. Gracias
Sujan Shrestha
De nada @SujanShrestha. Me alegra que haya ayudado.
Nikhil
4

Use el mapa y la dispersión de objetos para combinar las dos matrices:

var newArray = cartProducts.map(cart => ({
  ...cart,
  ...productDetails.find(prod => prod.productID === cart.productID)
}));
jaspenlind
fuente
Gracias por su respuesta. Muy apreciado.
Sujan Shrestha
De nada. Buen aspecto con tu proyecto.
jaspenlind
4

Convierta el productDetailsen un Mapa ( productDetailsMap), utilizando el productIDcomo la clave.

Itere el archivo cartProductscon el que Array.map()obtiene el producto actual productDetailsMappor él productID, y fusione esparciéndolo en un nuevo objeto.

const productDetails = [{"productID":1,"productTitle":"Product Title 1","productPrice":2000},{"productID":2,"productTitle":"Product Title 2","productPrice":5000},{"productID":3,"productTitle":"Product Title 3","productPrice":1000},{"productID":4,"productTitle":"Product Title 4","productPrice":10000}]
const cartProducts = [{"productID":1,"quantity":5},{"productID":3,"quantity":2}]

const productDetailsMap = new Map(productDetails.map(o => [o.productID, o]))

const result = cartProducts.map(o => ({
  ...productDetailsMap.get(o.productID),
  ...o
}))

console.log(result)

Ori Drori
fuente
1
Gracias por el código limpio. tu respuesta es muy limpia y simple. Gracias
Sujan Shrestha
3

Puedes probar algo similar a esto:

cartItemDetails() {
    return this.cartProducts.map(cp => {
         let prod = this.productDetails.find(pd => pd.productID === cp.productID)
         return {...cp, ...prod}
    })
}

Espero que esto ayude :)

Royson
fuente
Gracias por su respuesta. Muy apreciado.
Sujan Shrestha
3

Puede usar el Object.assign()método para copiar pares de propiedad-valor de productDetails en cartProducts siempre que el productID coincida:

let productDetails = [
            {
              productID: 1,
              productTitle: 'Product Title 1',
              productPrice: 2000
            },
            {
              productID: 2,
              productTitle: 'Product Title 2',
              productPrice: 5000
            },
            {
              productID: 3,
              productTitle: 'Product Title 3',
              productPrice: 1000
            },
            {
              productID: 4,
              productTitle: 'Product Title 4',
              productPrice: 10000
            }
          ];

let cartProducts = [
            {
              productID: 1,
              quantity: 5,
            },
            {
              productID: 3,
              quantity: 2,
            }
          ];
cartProducts.map(cart => Object.assign(cart, productDetails.find(product => product.productID === cart.productID))  )
console.log(cartProducts)

Addis
fuente
1
Gracias por su respuesta. Muy apreciado.
Sujan Shrestha
3
cartProducts.map(cartProduct => {
  return {
    ...productDetails.find(product => product.productID === cartProduct.productID),
    "quantity": cartProduct.quantity
  }
});

Podría hacer algunas comprobaciones nulas si es necesario.

Ashish Modi
fuente
Gracias por su respuesta. Muy apreciado.
Sujan Shrestha
3

Esto es lo que está jugando con su código aquí:

cartItemDetails() {
      return this.productDetails.filter(
        el => this.cartProducts.some(f => f.id === el.productID),
      );
    },

fque es un cartProductsartículo no tiene propiedadid .

Creo que lo que quisiste decir es f.productID lugar.

Ahora aquí hay una manera de agregar la quantitypropiedad usando la mapfunción:

this.productDetails = cartItemDetails().map((element) => {
  for (let e of this.cartProducts) {
    if (e.productID === element.productID) return {...element, quantity: e.quantity}
  }
})
Bradzer
fuente
Array cartProducts tenía un elemento de identificación en mi código local. Mientras publicaba la pregunta, la cambié para que fuera más clara. Y gracias por tu respuesta.
Sujan Shrestha