在Golang中创建多维嵌套的Map切片。

huangapple go评论96阅读模式
英文:

Creating Multi dimensional Nested Map slice in Golang

问题

TLDR; 这段代码的目的是将父亲和女儿的关系存储为父亲ID在数组中的索引。以下是等效的PHP代码。

我需要存储“父女”关系的值。有多个人是父亲,每个父亲都有多个女儿。有些父亲可能没有女儿。因此,我需要将值存储为:

variableName[DadID][indexFrom0ToAvailableValue] = {"id": id, "name": name}

其中indexFrom0toAvailableValue是女儿数量的索引,以及它们的idname

我正在做的是:

patu := make(map[int][]map[string]string)

p,n := 0,0

for _,c := range  dadhu {
    // 值为2的c.Daughter表示当前c是父亲
    if( c.Daughter == 2 ) {

        // 下面我使用len(daddhu)来确定可用行数。这会创建另一个错误,
        // 因为它会创建很多空白的map。

        patu[c.DadID] = make([]map[string]string, len(dadhu))

        // 在上面的数组中创建了带有`DadID`的数组`patu`,
        // 用于在下面的循环中存储它们的子女

        p++
    }
}
fmt.Println("Total Father is : ", p)

for _,c := range dadhu {
    // 值为1的c.Daughter表示当前c是女儿

    if ( c.Daughter == 1 ) {
        cID = strconv.Itoa(c.ID)
        patu[c.DadID][n] = map[string]string{"id": cID, "name" : c.Name}
        n++
    }
}

这段代码运行良好,但问题是它创建了如下的map:

map[44:[map[] map[] map[] map[] map[id: 45 name:Lana] map[] map[] map[] map[] map[id:46 name:Mana] map[] map[] map[] map[] map[id: 47 name:Bana].........] 28:[[map[] map[] map[] map[] map[id: 29 name:Lana] map[] map[] map[] map[] map[id:30 name:Mana] map[] map[] map[] map[] map[id: 31 name:Bana]........map[] map[] map[] map[]]] 

等等。

总共有5个父ID和49个总行数。

所以,你可以看到,有很多空白的map[]被创建。我需要清理这些空白的map。在存储女儿详细信息之前,先清理掉前4个空白的map。所以女儿的详细信息被存储在第5个map中。我假设如果有7个父亲,那么从4个空白的map变成每个6个空白的map。

除了在这里使用len(dadhu)时需要提供一些值之外,我没有找到任何逻辑错误。因为我不确定哪个父亲有多少个女儿。

如果这在所有方面都是错误的,请告诉我用golang实现的替代方法。

只是为了你的参考: 等效的PHP代码如下,它可以正常工作:

$patu = array();
$wod = array();
foreach ($dadhu as $e) {
    if ($e->isChild == '2') {
        $woc[] = $e->id;
        $patu[$e->id] = array();
    }
}
foreach($dadhu as $c) {
    if($c->isChild == '1') {
            if(in_array($c->dadID, $wod)) {
                $patu[$c->dadID][] = array($c->id, $c->name);
            }
        }
    }
英文:

TLDR; it's like storing value of child category as index of parent id in array. See equivalent PHP Code at end of block.

I need to store value of dad-daughter number. There are multiple person who are father and each father has multiple daughter. Some father may not have daughter either.So, I need to store value as :-

variableName[DadID][indexFrom0ToAvailableValue] = {"id": id, "name": name}

where indexFrom0toAvailableValue is index of number of daughter and their id and name.

What i am doing :-

patu := make(map[int][]map[string]string)

p,n := 0,0

for _,c := range  dadhu {
    // c.Daughter of value 2 means, current c is father
    if( c.Daughter == 2 ) {

        // Below i am using len(daddhu) to know
        // number of rows available. This is creating another bug
        // as it is creating lots of blank map.

        patu[c.DadID] = make([]map[string]string, len(dadhu))

        // Created array `patu` with `DadID` which will store 
        // their children below for range loop in above array

        p++
    }
}
fmt.Println("Total Father is : ", p)

for _,c := range dadhu {
    // c.Daughter of value 1 means, current c is daughter

    if ( c.Daughter == 1 ) {
        cID = strconv.Itoa(c.ID)
        patu[c.DadID][n] = map[string]string{"id": cID, "name" : c.Name}
        n++
    }
}

This is working fine, but my problem is, it is creating map like below :-

map[44:[map[] map[] map[] map[] map[id: 45 name:Lana] map[] map[] map[] map[] map[id:46 name:Mana] map[] map[] map[] map[] map[id: 47 name:Bana].........] 28:[[map[] map[] map[] map[] map[id: 29 name:Lana] map[] map[] map[] map[] map[id:30 name:Mana] map[] map[] map[] map[] map[id: 31 name:Bana]........map[] map[] map[] map[]]] 

and so on.

There are total 5 Parent ID and 49 Total number of Rows in mysql.

So, you can see, there are lots of blank map[] . Which get created. I need to clean this up. First 4 blank map each before storing daughter details. So daughter details are getting stored in 5th map . I am assuming if there will be 7 person who is father, than from 4 blank map it may become 6 blank map each.

I am not finding any logical mistake here except one where i am using len(dadhu) as i need to provide some value but i am not sure, which father has how many daughter.

Please let me know the alternate way to do this, if this is wrong in all ways in golang.

Just FYI : It's equivalent code in PHP - which is working fine is :

$patu = array();
$wod = array();
foreach ($dadhu as $e) {
    if ($e->isChild == '2') {
        $woc[] = $e->id;
        $patu[$e->id] = array();
    }
}
foreach($dadhu as $c) {
    if($c->isChild == '1') {
            if(in_array($c->dadID, $wod)) {
                $patu[$c->dadID][] = array($c->id, $c->name);
            }
        }
    }

答案1

得分: 4

在Go语言中,切片(Slices)是动态大小的,你不应该像对待数组那样处理它们。

在第一个循环中,如果你不知道确切的大小,请不要使用len(dadhu)来初始化切片。

相反,创建一个空的切片:

patu[c.DadID] = make([]map[string]string, 0)

在第二个循环中,向切片追加映射(maps):

patu[c.DadID] = append(patu[c.DadID], map[string]string{"id": cID, "name": c.Name})
英文:

Slices in Go are dynamically-sized, you shouldn't treat them like arrays.

In the first loop don't use len(dadhu) to initialize the slice if you don't know the exact size.

Instead, make an empty slice:

patu[c.DadID] = make([]map[string]string, 0)

In the second loop, append maps to it:

patu[c.DadID] = append(patu[c.DadID], map[string]string{"id": cID, "name": c.Name})

huangapple
  • 本文由 发表于 2017年7月25日 20:02:43
  • 转载请务必保留本文链接:https://go.coder-hub.com/45302708.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定