Home  >  Article  >  Backend Development  >  How can I efficiently group and sum a slice of structs based on specific fields in Golang?

How can I efficiently group and sum a slice of structs based on specific fields in Golang?

Barbara Streisand
Barbara StreisandOriginal
2024-11-02 20:47:03311browse

How can I efficiently group and sum a slice of structs based on specific fields in Golang?

Efficient Grouping and Summing of Struct Slices in Golang

In Golang, handling data efficiently is crucial. When dealing with slices of structs, tasks such as grouping and summing can become challenging. This guide addresses an efficient approach to group and sum a slice of structs based on specific fields.

Problem Statement

Consider the following struct:

type Register struct {
    id1 int
    id2 int
    id3 int
    id4 int
    id5 int
    id6 int
    id7 int
    id8 int
    money int
}

The goal is to group registers by the fields id1, id2, id3, id4, id5, id6, id7, and id8 and then sum the associated money field.

Solution

The provided solution involves slight refactoring of the struct types. By extracting the key fields into a separate struct, Key, we can utilize the comparability of structs in Golang.

Refactored Types

type Key struct {
    id1 int
    id2 int
    id3 int
    id4 int
    id5 int
    id6 int
    id7 int
    id8 int
}

type Register struct {
    key   Key
    money int
}

Grouping and Summing

To achieve grouping and summing, we create a map[Key]int. The Key of the map represents the combination of id fields, while the value represents the sum of money for registers with the same key.

regs := []*Register{
    {Key{id1: 345}, 1500},
    {Key{id1: 345, id2: 140}, 2700},
    {Key{id1: 345, id2: 140}, 1300},
    {Key{id1: 345}, 1000},
    {Key{id3: 999}, 1000},
    {Key{id3: 999}, 2000},
}

// calculate sum:
m := map[Key]int{}
for _, v := range regs {
    m[v.key] += v.money
}

Output

The map provides a grouped and summed representation of the registers.

map[{345 0 0 0 0 0 0 0}:2500 {345 140 0 0 0 0 0 0}:4000 {0 0 999 0 0 0 0 0}:3000]

Enhanced Output

For improved readability, we can format the output as follows:

fmt.Println("Nice output:")
for k, v := range m {
    fmt.Printf("%+3v: %d\n", k, v)
}

Result

Nice output:
{id1:345 id2:  0 id3:  0 id4:  0 id5:  0 id6:  0 id7:  0 id8:  0}: 2500
{id1:345 id2:140 id3:  0 id4:  0 id5:  0 id6:  0 id7:  0 id8:  0}: 4000
{id1:  0 id2:  0 id3:999 id4:  0 id5:  0 id6:  0 id7:  0 id8:  0}: 3000

Advantages

This approach offers several advantages:

  • Simplified grouping and summing using maps
  • Efficient handling of data by leveraging comparable structs
  • Flexibility in handling different grouping criteria through the use of the Key struct

The above is the detailed content of How can I efficiently group and sum a slice of structs based on specific fields in Golang?. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn