在进行过程中,是否可以通过某种方式动态地转换变量?

例如,如果一个简单的转换将是:

1
var intAge  = interfaceAge.(int)

如果我事先不知道年龄是整数怎么办? 一种简单的书写方式是

1
2
var x = getType()
var someTypeAge = interfaceAge(.x)

有没有办法实现这样的目标? 反射包提供了一些在运行时确定或强制转换类型的方法-但我找不到像上述提到的东西(适用于所有类型的通用方案)。

  • 进行中没有"广播"。见类型开关
  • 什么时候不知道x具有什么类型? Go是一种具有静态类型的语言。变量的类型在编译时总是已知的。变量的类型可能是接口类型。
  • 您正在寻找一种类型开关,该开关可让您根据(静态)类型列表确定行为。几乎可以肯定有一种方法可以做您希望做的任何事情,您能详细说明一下您的尝试吗?
  • 请参阅规格/文档。当且仅当foo是接口类型时,您才可以执行x := foo.(int)(或更常见的是foo.(T)。它是类型断言,如果接口不保存所要求的类型,它将在运行时惊慌。您可以使用x, ok := foo.(int),如果类型断言失败,则x为零值,ok为false。
  • OP没有按名称提及类型断言,但清楚地知道该功能(这就是初始示例所显示的内容)。这里的问题是关于任意类型的动态选择。实际上,可以通过直接分配来实现等效效果(但不会获得任何效果):someTypeAge := interfaceAge。您可以将interface{}类型的数据传递到您的心脏内容-某些功能(例如fmt.Println(interfaceAge))将动态处理数据。

不,你不能。 Go是一种静态类型的语言。 变量的类型在编译时

如果要动态确定interface{}type,则可以使用类型切换:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
var t interface{}
t = functionOfSomeType()
switch t := t.(type) {
default:
    fmt.Printf("unexpected type %T", t)       // %T prints whatever type t has
case bool:
    fmt.Printf("boolean %t
", t)             // t has type bool
case int:
    fmt.Printf("integer %d
", t)             // t has type int
case *bool:
    fmt.Printf("pointer to boolean %t
", *t) // t has type *bool
case *int:
    fmt.Printf("pointer to integer %d
", *t) // t has type *int
}
  • 谢谢。我不明白的是为什么Go是静态类型的事实意味着您不能在运行时转换类型。例如,在C#中,您可以做到这一点,C#也是一种静态类型语言。您能详细说明一下吗?
  • @orcaman:我认为您可能会将接口与泛型混淆。值的类型在运行时始终是已知的,因为在编译时是已知的。 Go中也对转换进行了很好的定义。
  • @orcaman在C#中,就像在Go中一样,将使用var ..推断您的类型。如果要显式定义类型,则还必须将其显式转换为所需的类型(除非将其装箱)。因此,我不确定是否能将您与C#的比较-情况相同。现在,如果您在谈论dynamic-那就是一个完全不同的野兽,当然不能保证编译时类型的安全。
  • @SimonWhitehead谢谢。在C#示例中,我的意思是您可以执行以下操作:var type = obj.GetType();返回Activator.CreateInstance(type)为T;创建任何类型的实例而无需事先知道类型。在使用过程中,我可以动态获取类型,但是我似乎无法创建该类型的变量(我自己无需编写覆盖所有类型的丑陋switch语句)。
  • @fabrizioM-如果您添加有关类型切换的部分(golang.org/doc/effective_go.html#type_switch),因为它可能与我想要达到的目标接近,我会接受答案(正确,但可能是对于希望做类似事情的人来说更有帮助。谢谢!
  • 为什么不提及类型断言?这似乎(几乎是?)是OP想要的。