Is there a way to determine the total sum of data within a multidimensional object using typescript?

I am currently working on the following code snippet:

import { HttpClient } from "@angular/common/http";
import { Component, OnInit } from "@angular/core";
import { FormBuilder, FormGroup, Validators } from "@angular/forms";
import { ActivatedRoute, Router } from "@angular/router";

@Component({
  styleUrls: ["./styles.scss"],
  templateUrl: "./template.html"
})
export class MyRouteData {
  MyDataObject: object;
  MyDataObjectTotals: object;

  constructor(private http: HttpClient) {}

  ngOnInit() {
    this.http
      .get("http://localhost:5000/MyRoute/GetMyData")
      .subscribe(response => {
        console.log(response);
        this.MyDataObject = response;
      });
  }
}

The data stored in the MyDataObject object is as follows:

{
  "Record1": {
    "CustomerName": "Obi Wan Kenobi",
    "TransactionDate": "2018-01-01",
    "IsNewCustomer": false,
    "ItemPuchased":"Speeder Polish 250ml",
    "QuantityPurchased":2,
    "SalesTotal":10.04
  },
  "Record2": {
    "CustomerName": "Darth Vader",
    "TransactionDate": "2018-01-02",
    "IsNewCustomer": false,
    "ItemPuchased":"Burn Cream 250ml",
    "QuantityPurchased":200000,
    "SalesTotal":7523840.84
  },
  ...
}

Currently, I would like to calculate the totals of each column and store them in another object (defined as MyDataObjectTotals).

I have managed to sum up a single column using the following code:

var QuantityPurchasedColumn = MyDataObject.map(a => a.QuantityPurchased);
var QuantityPurchasedTotal = QuantityPurchasedColumn.reduce(function(a, b) {return a + b;});

Is there a more generic method that can take an object (such as MyDataObject) and return an object containing the total values for each column?

{
    "CustomerName": null,
    "TransactionDate": null,
    "IsNewCustomer": null,
    "ItemPuchased":null,
    "QuantityPurchased": 200008,
    "SalesTotal": 7675174.90
}

Answer №1

From your successful use of map, it seems like you intended for MyDataObject to be an array rather than an object as shown in the initial question. You can loop through the keys of the first record using a for-in loop and determine, for each key, whether you want to calculate a sum or return null.

var MyDataObject = [
  {
    "CustomerName": "Obi Wan Kenobi",
    "TransactionDate": "2018-01-01",
    "IsNewCustomer": false,
    "ItemPuchased": "Speeder Polish 250ml",
    "QuantityPurchased": 2,
    "SalesTotal": 10.04
  },
  {
    "CustomerName": "Darth Vader",
    "TransactionDate": "2018-01-02",
    "IsNewCustomer": false,
    "ItemPuchased": "Burn Cream 250ml",
    "QuantityPurchased": 200000,
    "SalesTotal": 7523840.84
  },
  {
    "CustomerName": "Luke Skywalker",
    "TransactionDate": "2018-01-02",
    "IsNewCustomer": false,
    "ItemPuchased": "Power Converters",
    "QuantityPurchased": 5,
    "SalesTotal": 1324.02
  },
  {
    "CustomerName": "Jabba the Hut",
    "TransactionDate": "2019-01-05",
    "IsNewCustomer": false,
    "ItemPuchased": "Dancing Slave Chick",
    "QuantityPurchased": 1,
    "SalesTotal": 150000.00
  }
];
type MyRecord = typeof MyDataObject[number];

var SumColumns: Partial<{ [K in keyof MyRecord]:
  MyRecord[K] extends number ? true : never }> = {
  "QuantityPurchased": true,
  "SalesTotal": true
};

var Sum = <{ [K in keyof MyRecord]: number | null }>{};
let columnName: keyof MyRecord;
for (columnName in MyDataObject[0]) { 
  Sum[columnName] = SumColumns[columnName]
    ? MyDataObject.map(a => <number>a[columnName]).reduce(function (a, b) { return a + b; })
    : null;
}

Answer №2

Have you experimented with using the JSON.Parse(myObject) method? This will effectively transform your JSON object into a JavaScript object.

Answer №3

When tackling this issue, I have come up with 2 distinct strategies. 1. Traverse through the JSON keys.

var myObj = {

  "Record1": {
    "CustomerName": "Obi Wan Kenobi",
    "TransactionDate": "2018-01-01",
    "IsNewCustomer": false,
    "ItemPuchased":"Speeder Polish 250ml",
    "QuantityPurchased":2,
    "SalesTotal":10.04
  },
    "Record2": {
    "CustomerName": "Oobi",
    "TransactionDate": "2018-01-01",
    "IsNewCustomer": false,
    "ItemPuchased":"Speeder Polish 250ml",
    "QuantityPurchased":2,
    "SalesTotal":10.04
  },
};

for (var values in myObj) {
  console.log(myObj[values]['QuantityPurchased']);
}

2. Opt for an array of Records instead of JSON data.

var myObj: Records[] = [

   {
    "CustomerName": "Obi Wan Kenobi",
    "TransactionDate": "2018-01-01",
    "IsNewCustomer": false,
    "ItemPuchased":"Speeder Polish 250ml",
    "QuantityPurchased":2,
    "SalesTotal":10.04
  },
 {
    "CustomerName": "Oobi",
    "TransactionDate": "2018-01-01",
    "IsNewCustomer": false,
    "ItemPuchased":"Speeder Polish 250ml",
    "QuantityPurchased":2,
    "SalesTotal":10.04
  },
];

myObj.forEach(myRecord => {
  // Perform actions as needed.
});

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

Why is my ASP.NET Core Crud request failing with incorrect method matching?

I am facing an issue with the third method in my Angular ASP.NET Core Controller. The first two methods work fine, but the GetBookItemsByTitle does not seem to be firing correctly. As I am still learning, I believe my mistake here is obvious. /// <summ ...

Creating adaptable Object Properties using Zod

Just dipping my toes into Typescript, Zod, and Trpc. Let's say I have a schema for animals and plants. I want to keep all their shared properties in the main part of the schema, while putting more specific details into a sub-object named custom. (jus ...

Unraveling nested objects using ts.data.json: A step-by-step guide

I'm experimenting with the code example found at https://github.com/joanllenas/ts.data.json to decode and validate a JSON payload in Typescript. While it works fine, my goal is to apply this concept to nested data structures, such as having a User obj ...

Angular 5 and the world of HTTP connections

As I embark on my journey of creating my very first Angular 5 application, one of the key components is its interaction with the Java Rest Web Services that I have developed using Spring Boot. The foundation of this integration lies in the following RESTfu ...

Error when compiling with Component Lab's Autocomplete function for SVG Icons in Material UI

Upon running my project on the browser, I encountered the following error: Error message: ./node_modules/@material-ui/lab/esm/internal/svg-icons/Close.js Attempted import error: 'createSvgIcon' is not exported from '@material-ui/core/utils ...

Using inline style instead of relying on the quill editor's built-in classes, as classes may not be accessible in order to render HTML effectively

I have integrated the ngx-quill editor into my Angular project as the rich text editor. I plan to save the generated HTML in a database and display it on various browsers using innerHTML. Since the styling is done through a class attribute that references ...

Saving a user with a BLOB avatar in Angular 5: Tips and Tricks for Success

As a newcomer to Angular, I am trying to figure out how to properly save a new user with an avatar. Can someone help me understand how to pass the Blob value of the avatar to my user Model for successful saving? Below is the code snippet I am working with ...

Guide on executing a function exclusively when the state of a service variable changes within an Angular4 component

In my InfoFormService, I have a variable called isInValidating that is initially set to false. This variable becomes true when the component calls the validateEmail(email) function as shown below. @Injectable() export class InfoFormService { private ...

Using alternate variables in the watchQuery() function in Apollo Angular will generate the cached data

Currently, I am implementing a feature in my project that allows users to access and analyze data based on various parameters such as year, location, and gender. Below is the code snippet that I have developed for this feature: this._querySubscription = ...

Angular Form Required not functioning as expected

I have encountered an issue with my form where the required attribute does not seem to work properly. Even when I leave the input field empty, the form still gets submitted. Here is a snippet of my code: <div class="form-group"> <div class="c ...

Updating the value of a dynamic ngModel in Ionic3

Does anyone know how to change the value of ngModel in Ionic 3 framework? I need to programmatically toggle all ion-toggle elements. component: allRecs:any; constructor(){ this.allRecs = [ { label: "label 1", model : "model1" }, ...

Alter the data displayed by the Radio button using Angular when the Submit button is clicked

I've encountered an issue where I need to alter a div based on the selection of a radio button. Currently, it changes instantly upon button click, rather than waiting for submission. My desired outcome is for the value to be submitted when the button ...

Angular 4 - Seeking clarification on the usage of *ngComponentOutlet

When using *ngComponentOutlet, the following code snippets are employed to handle the displaying: Below is a snippet of functional code: this.displayComponent({ 'objects':[ {component: ToDisplayAComponent, expanded: fals ...

"Utilizing TypeScript to assign specific types to recognized keys while also accommodating for undefined

Is there a way to declare an object in such a manner that it requires certain keys, while also allowing for the inclusion of any other keys? Let's say we have an object called student which must always include the keys name and gender, but can also h ...

How can you modify the height of the header field in Grid?

I have a single grid-tile: <md-grid-tile class="header"> <md-card class="content"> <md-card-header> <md-card-title>Monday</md-card-title> <md-card-subtitle>29.03.17</md-card-subtitle> ...

What is the reason behind the prevalence of using export class xxx in angular4 projects instead of export default class xxx?

Understanding the distinction between export class xxx and export default class xxx is crucial. However, I've noticed that numerous angular4 projects utilize export class xxx in this manner: @Component({ selector: 'call-record', templ ...

The Rx subject has not been initialized

Within this particular Namespace, I am exporting a Rx subject of the string data type: namespace something.TaskHandling { export const selectedTask$ = new Rx.Subject<String>(); Inside my TaskListComponent class within the something.TaskHandling. ...

It is not possible to execute an injectable function using a service instance, as the parameter value consistently stays as null

I am utilizing an angular web app that relies on access tokens that have the potential to expire. When they do expire, a 401 status response is sent back to the app, triggering processing by a retryWhen operator. The logic for initiating a token refresh AP ...

Tips for solving caching problems in an Angular application on a web browser

My Angular application undergoes a deployment pipeline where we utilize the "ng build --prod" command to build the application. Each time we make code changes, this command generates a unique hashcode for the build files. However, we are encountering an ...

Issue with building Webpack React Router DOM configuration

I recently developed a React+Typescript app with Webpack 5 configuration completely from scratch. Everything was running smoothly in development mode, and I utilized React Router DOM version 6.23.1 for routing. However, once I built the app, some component ...