What are the steps for performing projection in TypeScript?

Looking to fill up the orders array, which consists of objects of type Order. The desired output is

orders=[{id:1,qt:4},{id:2, qt:2},{id:3,qt:2}]
. How can I achieve this using TypeScript? I am new to this language.

export class Product {
  constructor(public id: number, public name: string, public price: number) {}
}
export interface Order {
  id: number;
  qt: number;
}

export const products: Product[] = [
  new Product(1, 'Apple', 2.1),
  new Product(2, 'Banana', 2.2),
  new Product(3, 'Chocolate', 2.3),
  new Product(4, 'Dessert', 2.4),
];

export const cart: Product[] = [
  products[0],
  products[0],
  products[2],
  products[1],
  products[2],
  products[0],
  products[1],
  products[0],
];

export const orders: Order[] = [];

Edit

For those wondering how

orders=[{id:1,qt:4},{id:2, qt:2},{id:3,qt:2}]
is achieved.

In the cart:

  • the quantity of apples (id:1) is qt:4
  • the quantity of bananas (id:2) is qt:2
  • the quantity of chocolates (id:3) is qt:2

Therefore, by utilizing the cart, the objective is to obtain

orders=[{id:1,qt:4},{id:2, qt:2},{id:3,qt:2}]
. This should clarify things.

Answer №1

If you're searching for a solution similar to LINQ, then you may want to consider using higher order functions like map, filter, and reduce.

While LINQ projections may not directly solve your problem, they are essentially representations of map (Select), concatMap/flatMap (SelectMany), and zip (Zip). Your task revolves around counting the occurrences of each id within the entire array.

Most data manipulation challenges can be tackled with higher order folds such as reduce in JavaScript or Aggregate in C#. In this case, you start by counting the occurrences of each id and create a counter object as explained here.

cart.reduce((acc, { id }) => {
    acc[id] = (acc[id] ?? 0) + 1;
    return acc;
}, {} as Record<number, number>);

Essentially, you initiate the fold operation with an empty object and increment the count for each id in the array. If the id is not present, the nullish coalescing operator (acc[id] ?? 0) assigns and increments the count using 0.

This process yields-

{ '1': 4, '2': 2, '3': 2 }

Next, you need to transform this into-

[ { id: 1, qt: 4 }, { id: 2, qt: 2 }, { id: 3, qt: 2 } ]

By applying Object.entries to the fold result, you get-

> Object.entries({ '1': 4, '2': 2, '3': 2 })
[ [ '1', 4 ], [ '2', 2 ], [ '3', 2 ] ]

Finally, a simple map operation is sufficient-

Object.entries(...).map(([id, qt]) => ({ id: Number(id), qt }))

By combining all these steps, you get-

export const orders: Order[] = Object.entries(
    cart.reduce((acc, { id }) => {
        acc[id] = (acc[id] ?? 0) + 1;
        return acc;
    }, {} as Record<number, number>)
).map(([id, qt]) => ({ id: Number(id), qt }));

It's worth noting that Object.entries might not be the most efficient as it generates an array instead of an iterator. If efficiency is a concern, consider implementing an iterator version of Object.entries using generator functions-

function* objEntries<T>(x: Record<string, T>): IterableIterator<[string, T]> {
  for (const k in x) {
    yield [k, x[k]];
  }
}

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

Unable to redirect to another page in React after 3 seconds, the function is not functioning as intended

const homeFunction = () => { const [redirect, setRedirect] = useState<boolean>(false); const [redirecting, setRedirecting] = useState<boolean>(false); const userContext = useContext(UserContext); useEffect(() => { const valu ...

Ng-repeat seems to be having trouble showing the JSON data

Thank you in advance for any assistance. I have a factory in my application that utilizes a post method to retrieve data from a C# function. Despite successfully receiving the data and logging it to the console, I am facing difficulties in properly display ...

What is the best way to deliver an HTML document in Express from a directory that is one level higher than my server folder?

I am facing an issue while trying to access an HTML file from my main directory through my Express server, which is located one level deeper in the server folder. Below is the configuration of my server code: const express = require('express') ...

Instructions for showing a timer on a webpage from a managed bean by utilizing JavaScript

I'm currently tackling the challenge of passing a Date from a managed bean to JavaScript and then displaying it as a timer in the format "hh:mm:ss aa". I've attempted it but so far, no luck. Code: DateTimeManagmentMB.java (Managed Bean) import ...

Issue encountered when attempting to connect an external script to a Vue single file component

Struggling to link an external script to a single file component in Vue. My project setup is as follows: https://i.sstatic.net/LWvNx.png I need to link the file components/Sshy to ../javascripts/ I have successfully linked other scripts using either of ...

Teaching you how to incorporate empty spaces and punctuation within JOI

How can I modify Joi to permit spaces/whitespaces in a title field within a form? Scheduled to work with Jude tomorrow. I want to allow entries like: Morningwalk Currently, only the second example is passing validation. Below is my existing Joi val ...

To manipulate the array in a more complex manner, either add or remove the item based on its existence: if it's already in the array, remove it; if it

As I prepare to send key-value pairs to the backend in the form of a JSON structure, each representing a category (e.g., customer churn rate), I encounter an issue. The idea is to add checkmarked options to the array of their respective categories. However ...

"Unlocking the JSON element with jQuery Ajax: A step-by-step guide

I am trying to pinpoint a specific element within my JSON data: { "taskMeta": "Some meta info", "tasksLib": [ { "task001": { "id":"1", "createDate":"01.02.17", "dueDate":"02.03.17", "au ...

How can I retrieve the class of the parent element by referencing the child id in jQuery?

I want to trigger an alert on click from the child id <th id="first"> to the table(parent) class. alert($(this).parent('tr').attr('class')); This code helped me to get the class of the <tr>. However, when I try to get the ...

What is the best way to include text in an editor access notification email?

I've developed a script to assign editors to a spreadsheet, but I'm looking to personalize the emails sent to them. The screenshot below illustrates the step where I can input a message for the email recipients who have been granted access. f ...

What are the steps to effectively utilize the $filter('filter') function when filtering multiple columns with OR as the condition?

In my AngularJs Application, I have a collection of customers. var customers = [ { "Name": "Alfreds Futterkiste", "City": "Berlin", "Country": "Germany" }, { "Name": "Ana Trujillo Emparedados y helados", ...

What is the best way to create a full bleed background image that adjusts to different screen resolutions using CSS and JavaScript?

Similar Question: Full Screen Background Image in Firefox Check out: Is there a way to achieve a similar effect on a website where the content adjusts to different monitor resolutions? On the Ingress site, it seems like everything scales proportional ...

"Upon setting the state in React, the Full Calendar refreshes and retrieves events

My current setup involves using the FullCalendar API to fetch events as shown below: <FullCalendar ref={calendarRef} plugins={[listPlugin, bootstrap5Plugin]} initialView='listMonth' ...

How can I incorporate Bootstrap multi-select into the jQuery DataTables DOM?

Having trouble implementing a bootstrap multi-select inside a jQuery datatable DOM. I followed this example to add a custom element within the jQuery datatable container. It works fine for normal bootstrap select, but when trying to add a bootstrap multi-s ...

Guide on extracting part of a string in JavaScript from a specific starting point to a designated character

Currently working on a JavaScript project where I am in need of extracting words enclosed within two brackets. For example: [Green]- Amazon I specifically require the word "Green" from within the brackets. Using indexOf() won't work as there could ...

Encountering the "potential null object" TypeScript issue when utilizing template ref data in Vue

Currently, I am trying to make modifications to the CSS rules of an <h1> element with a reference ref="header". However, I have encountered a TypeScript error that is preventing me from doing so. const header = ref<HTMLElement | null> ...

Determine the instance's name as a string in JavaScript

Currently, I am utilizing Three.js in combination with javascript. Upon running the following line of code: console.log(this.scene.children[1]) I receive the following output in the console within Chrome: https://i.stack.imgur.com/6LBPR.png Is there a w ...

What is the best way to remove this .click function?

My goal is to create a switch function where clicking the "on" button changes its CSS, and if the user then clicks on the "off" button, the CSS returns to normal. I also need the switch to default to the "on" position, but my attempts so far have been unsu ...

JavaScript error: Resource could not be loaded

When I have a js function called by an onclick event in a radio button, it doesn't work if the function is placed in the same ascx file where the radio button is defined. To resolve this issue, I moved the function to the ascx that includes the ascx w ...

Learning about the intricacies of backend Node.js through Angular using GET requests

I am having trouble retrieving the query parameters from a frontend GET request on the backend side. I have attempted to use url and query, but still need assistance fetching the query on the nodejs side. Can someone recommend a method that would allow me ...