【问题标题】:What does it mean for a constant to be untyped?常量无类型是什么意思?
【发布时间】:2020-03-18 15:34:59
【问题描述】:

Go Programming Language Specification 说:

常量可以有类型也可以无类型

我对自己的理解有点怀疑。 考虑一下规范中的这个例子:

const l = "hi"             // l == "hi"  (untyped string constant)
const m = string(k)        // m == "x"   (type string)

规范说:

constant 可以通过常量声明显式地赋予一个类型,或者 转换,或在变量声明或变量中使用时隐式转换 赋值或作为表达式中的操作数

通过这句话,为什么不输入l,因为它显然是一个常量声明?

使用另一个example,这种行为更清楚

type Foo string
func f(a Foo) {}

func main() {
  f("sarkozy")

  const t = "julie gayet"
  f(t)

  s := "hollande"

  //compile error
  // f(s)

  f(Foo(s)) // ok
}

f("sarkozy") 编译的原因是由于规范中关于可分配性的声明吗?

x 是一个无类型的常量,可以用 T 类型的值表示。

我的论点如下:

  • “sarkozy”是一个无类型的文字。
  • 因此“sarkozy”可以用Foo 表示,这意味着我可以像 Foo("sarkozy") 那样键入强制
  • f(s) 失败,因为 s 不是无类型

【问题讨论】:

标签: go


【解决方案1】:

为什么不输入 l ,因为它显然是一个常量声明?

是的,这显然是一个常量声明,正如您的报价所说:

常量可以通过常量声明显式地被赋予一个类型

但是,在您的情况下,没有明确给出的类型。只有当“用于变量声明或赋值或作为表达式中的操作数”时,您才能拥有隐式给定的类型

f("sarkozy") 编译的原因是由于规范中关于可分配性的声明吗?

是的,f("sarkozy") 编译的原因是因为“sarkozy”的无类型常量在用作表达式中的操作数时具有隐式给出的类型,例如您的情况。

“sarkozy”被隐式地赋予Foo的类型

那么为什么f(s) 不编译?(好吧,这不是问题,但问题仍然存在)

您的论点指出:“f(s) 失败,因为 s 不是无类型的。”

s 确实不是无类型的。 s是变量而不是常量,变量不能无类型。

Variable Declarations 的 Go 规范声明:

如果类型不存在并且相应的表达式计算为无类型常量,则声明变量的类型如 §Assignments 中所述。

根据我的理解,指的是以下内容:

根据值是布尔、符文、整数、浮点、复数还是字符串常量,首先将常量分别转换为 bool、rune、int、float64、complex128 或 string 类型。

所以,下面一行:

s := "hollande"

将声明string 类型的变量(非常量)s,因为右边的表达式是一个无类型的字符串常量。类型是在变量声明期间隐式给出的,而不是通过分析它稍后将使用的上下文。

f(s) 将导致编译错误,因为您尝试使用 string 类型的值,而应该使用 Foo 类型的值。

【讨论】:

  • 谢谢。这个“变量不能无类型”是我理解的关键。
猜你喜欢
  • 1970-01-01
  • 2016-09-15
  • 2012-04-21
  • 2015-02-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-01-03
  • 1970-01-01
相关资源
最近更新 更多