【问题标题】:How to override inbuilt type如何覆盖内置类型
【发布时间】:2015-08-12 20:43:27
【问题描述】:

默认time.Duration2h0m0s 等格式打印。

但是,我想将其打印为2 Hours2 Hours 1 Min

我可以这样做的一种方法是创建一个新的struct TimeDurationStruct 并创建一个String() 函数。我在golang playground做了同样的事情

工作代码

package main

import (
    "fmt"
    "time"
    "math"
)

type TimeDurationStruct struct {
    t time.Duration
}

func (i *TimeDurationStruct) Set(t time.Duration) {
    i.t = t
}

func (i TimeDurationStruct) String() string {
    duration := i.t

    var dayString, hourMinString string
    var days, hours float64

    totalHours := duration.Hours()
    minutes := math.Mod(duration.Minutes(), 60.0)
    if totalHours < 24.0 {
        hours = totalHours
    } else {
        hours = math.Mod(totalHours, 24.0)
        days = totalHours / 24.0
    }

    if hours == 0 {

    } else if hours < 1 {
        if minutes == 1 {
            hourMinString = "1 Min"
        } else {
            hourMinString = fmt.Sprintf("%g Mins", minutes)
        }
    } else if hours >= 1 && hours < 2 {
        if minutes == 0 {
            hourMinString = "1 Hour"
        } else if minutes == 1 {
            hourMinString = "1 Hour 1 Min"
        } else {
            hourMinString = fmt.Sprintf("1 Hour %g Mins", minutes)
        }
    } else {
        if minutes == 0 {
            hourMinString = fmt.Sprintf("%g Hours", hours)
        } else if minutes == 1 {
            hourMinString = fmt.Sprintf("%g Hours 1 Min", hours)
        } else {
            hourMinString = fmt.Sprintf("%g Hours %g Mins", hours, minutes)
        }
    }

    if days > 0 {
        if days == 1 {
            dayString = "1 Day"
        } else {
            dayString = fmt.Sprintf("%g Days ", days)
        }
    }

    return dayString + hourMinString
}

func main() {
    t := time.Now()
    d := t.Add(2 * time.Hour).Sub(t)
    fmt.Println(d)
    var i TimeDurationStruct
    i.Set(d)
    fmt.Println(i)
}

问题

  1. 是否可以覆盖time.Duration type 而不是结构类型。例如

    type TimeDurationStruct time.Duration
    

    我试过here,但是不行……

  2. 有没有更好/更简单的方法?

【问题讨论】:

  • 另一个问题有an answer,它显示了嵌入(顺便说一句,您可能应该在这里而不是非导出的命名字段)和非嵌入自定义之间的区别time.Time 类型。
  • 我更新了问题,关于我是否只能覆盖 time.Duration 类型的 String() 函数。太棒了,我现在使用嵌入式类型并且可以工作play.golang.org/p/tWyd48ajpl

标签: struct go interface


【解决方案1】:

从您的问题编辑开始,是的,您可以在没有结构的情况下实现此效果。问题是当你定义你的类型时:

type TimeDurationStruct time.Duration

您的新 TimeDurationStruct 类型不会像使用类型嵌入选项时那样从 time.Duration 继承任何方法。您仍然可以访问这些方法,但您需要执行类型转换。因此,您的 String 方法的开头应修改为:

func (i TimeDurationStruct) String() string {
    duration := time.Duration(i)
    ...

【讨论】:

    猜你喜欢
    • 2013-02-21
    • 1970-01-01
    • 1970-01-01
    • 2021-05-03
    • 2021-12-09
    • 1970-01-01
    • 2019-08-26
    • 1970-01-01
    • 2019-05-09
    相关资源
    最近更新 更多