duan41497 2018-10-04 07:25
浏览 50
已采纳

构造奇怪的行为

I just started to play with Go-lang and come across a Strange behavior of it Structs. I have a Struct A and another Struct B, in Struct B one key defined as []A the problem is when assigning the value of new instance type of B as elements of A it throw error despite the types are same. Any help will be greatly appreciated Below here I am pasting the minimal code which cause error

package main

import (
    "fmt"
    "math"
    "github.com/shirou/gopsutil/disk"
    "strconv"
)

func main() {

    /************ disk details goes here ************/
    diskPartitions, err := disk.Partitions(true)
    dealwithErr(err)
    fmt.Println(diskPartitions)

    type PARTITIONLIST []PARTITION
    var partitionsList PARTITIONLIST

    for partitionIndex, partition := range diskPartitions {
        partitionStat, err := disk.Usage(partition.Mountpoint)
        dealwithErr(err)

        var partitionDetails = PARTITION{
            "PARTITION",
            partitionIndex,
            partition.Mountpoint,
            "" + fmt.Sprint(partitionStat.Total) + " and " + bytesToSize(partitionStat.Total),
            "" + fmt.Sprint(partitionStat.Used) + " and " + bytesToSize(partitionStat.Used),
            "" + fmt.Sprint(partitionStat.Free) + " and " + bytesToSize(partitionStat.Free),
            "" + fmt.Sprint(partitionStat.UsedPercent) + "and " + strconv.FormatFloat(partitionStat.UsedPercent, 'f', 2, 64),
        }

        partitionsList = append(partitionsList, partitionDetails)
    }

    //till here working fine
    fmt.Println(partitionsList)

    //THE BELOW TWO LINES ERROR IS THE ACTUAL ERROR I AM ASKING
    var partitionDetails = PARTITIONS{
        "partitions",
        partitionsList
    }



    dealwithErr(err)
}

/************ all struct goes here ************/

type PARTITION struct {
    Name                   string
    Partition_index        int
    Partition              string
    Total_space_in_bytes   string
    Used_space_in_bytes    string
    Free_space_in_bytes    string
    Percentage_space_usage string
}

type PARTITIONLIST []PARTITION

type PARTITIONS struct {
    Name                string
    List                []PARTITIONS
}

/************ helper functions goes below here ************/
func bytesToSize(bytes uint64) string {
    sizes := []string{"Bytes", "KB", "MB", "GB", "TB"}
    if bytes == 0 {
        return fmt.Sprint(float64(0), "bytes")
    } else {
        var bytes1 = float64(bytes)
        var i = math.Floor(math.Log(bytes1) / math.Log(1024))
        var count = bytes1 / math.Pow(1024, i)
        var j = int(i)
        var val = fmt.Sprintf("%.1f", count)
        return fmt.Sprint(val, sizes[j])
    }
}

func dealwithErr(err error) {
    if err != nil {
        fmt.Println(err)
    }
}

EDIT: that error am getting on run time

unexpected newline, expecting comma or }

and that warning editor show on IDE

Cannot use partitionsList (type PARTITIONSLIST) as type []PARTITIONS

  • 写回答

2条回答 默认 最新

  • douaipi3965 2018-10-04 07:58
    关注

    As the error clearly says:

    Cannot use partitionsList (type PARTITIONSLIST) as type []PARTITIONS

    You have type mismatch problem in the struct. Since PARTITIONSLIST is not qualy to []PARTITIONS. So if you create variable of both types they are different.

    type PARTITIONLIST []PARTITION
    
    type PARTITIONS struct {
        Name                string
        List                []PARTITIONS // here the list is slice of Partitions.
    }
    

    While when you are creating a slice of PARTITIONLIST type.

    var partitionsList PARTITIONLIST // this is a variable of PARTITIONLIST type which is not equal to `[]PARTITIONS`
    

    This is because golang is strictly typed language. So even if the underlying type of both values are similar. The are still different. To be more simple Try this example:

    package main
    
    import "fmt"
    
    type MyInt int
    
    func main() {
        var a int = 2
        var b MyInt = 2
        fmt.Println(a==b)
    }
    

    Output:

    invalid operation: a == b (mismatched types int and MyInt)

    Playground Example

    So you need to create a slice of []PARTITIONS as:

    var partitionsList `[]PARTITIONS`
    

    or you can create both variables of PARTITIONLIST type to make them similar.

    Another error:

    unexpected newline, expecting comma or }

    is because you need to pass , after last field if you are using it in new line as:

    var partitionDetails = PARTITIONS{
        "partitions",
        partitionsList, // pass comma here in your code.
    }
    

    Full working example :

    package main
    
    import (
        "fmt"
        "math"
        "strconv"
    
        "github.com/shirou/gopsutil/disk"
    )
    
    func main() {
    
        /************ disk details goes here ************/
        diskPartitions, err := disk.Partitions(true)
        dealwithErr(err)
        fmt.Println(diskPartitions)
    
        var partitionsList PARTITIONLIST
    
        for partitionIndex, partition := range diskPartitions {
            partitionStat, err := disk.Usage(partition.Mountpoint)
            dealwithErr(err)
    
            var partitionDetails = PARTITION{
                "PARTITION",
                partitionIndex,
                partition.Mountpoint,
                "" + fmt.Sprint(partitionStat.Total) + " and " + bytesToSize(partitionStat.Total),
                "" + fmt.Sprint(partitionStat.Used) + " and " + bytesToSize(partitionStat.Used),
                "" + fmt.Sprint(partitionStat.Free) + " and " + bytesToSize(partitionStat.Free),
                "" + fmt.Sprint(partitionStat.UsedPercent) + "and " + strconv.FormatFloat(partitionStat.UsedPercent, 'f', 2, 64),
            }
    
            partitionsList = append(partitionsList, partitionDetails)
        }
    
        //till here working fine
        fmt.Println(partitionsList)
    
        //THE BELOW TWO LINES ERROR IS THE ACTUAL ERROR I AM ASKING
        var partitionDetails = PARTITIONS{
            "partitions",
            partitionsList,
        }
    
        fmt.Println(partitionDetails)
    
        dealwithErr(err)
    }
    
    /************ all struct goes here ************/
    
    type PARTITION struct {
        Name                   string
        Partition_index        int
        Partition              string
        Total_space_in_bytes   string
        Used_space_in_bytes    string
        Free_space_in_bytes    string
        Percentage_space_usage string
    }
    
    type PARTITIONLIST []PARTITION
    
    type PARTITIONS struct {
        Name string
        List PARTITIONLIST
    }
    
    /************ helper functions goes below here ************/
    func bytesToSize(bytes uint64) string {
        sizes := []string{"Bytes", "KB", "MB", "GB", "TB"}
        if bytes == 0 {
            return fmt.Sprint(float64(0), "bytes")
        } else {
            var bytes1 = float64(bytes)
            var i = math.Floor(math.Log(bytes1) / math.Log(1024))
            var count = bytes1 / math.Pow(1024, i)
            var j = int(i)
            var val = fmt.Sprintf("%.1f", count)
            return fmt.Sprint(val, sizes[j])
        }
    }
    
    func dealwithErr(err error) {
        if err != nil {
            fmt.Println(err)
        }
    }
    

    Playground example

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论
查看更多回答(1条)

报告相同问题?

悬赏问题

  • ¥15 树莓派与pix飞控通信
  • ¥15 自动转发微信群信息到另外一个微信群
  • ¥15 outlook无法配置成功
  • ¥30 这是哪个作者做的宝宝起名网站
  • ¥60 版本过低apk如何修改可以兼容新的安卓系统
  • ¥25 由IPR导致的DRIVER_POWER_STATE_FAILURE蓝屏
  • ¥50 有数据,怎么建立模型求影响全要素生产率的因素
  • ¥50 有数据,怎么用matlab求全要素生产率
  • ¥15 TI的insta-spin例程
  • ¥15 完成下列问题完成下列问题