Confused with Type conversions in golang

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

Confused with Type conversions in golang

问题

我最近尝试学习golang。但是我对来自https://tour.golang.org/basics/13的这段代码感到困惑。

package main

import (
	"fmt"
	"math"
)

func main() {
	var x, y int = 3, 4
	var f float64 = math.Sqrt(float64(x*x + y*y))
	var z uint = uint(f)
	fmt.Println(x, y, z)
}

这段代码运行良好。然后我尝试了

var f = math.Sqrt(9 + 16)

这也可以工作。但是当我将其更改为var f = math.Sqrt(x*x + y*y)时,为什么它不起作用?它显示cannot use x * x + y * y (type int) as type float64 in argument to math.Sqrt

我有JavaScript的背景,但我无法理解上面的代码。

英文:

I recently tried to learn golang. But I got confused with this code from https://tour.golang.org/basics/13.

package main

import (
	"fmt"
	"math"
)

func main() {
	var x, y int = 3, 4
	var f float64 = math.Sqrt(float64(x*x + y*y))
	var z uint = uint(f)
	fmt.Println(x, y, z)
}

That one works well. Then I tried

var f = math.Sqrt(9 + 16)

which also works. But when I change it to var f = math.Sqrt(x*x + y*y) why is it not working? It says cannot use x * x + y * y (type int) as type float64 in argument to math.Sqrt

I have javascript background, and I somehow can't understand the code above.

答案1

得分: 7

math.Sqrt 函数的签名:

func Sqrt(x float64) float64

要求你传递 float64 类型的参数。

在这种情况下:

var f float64 = math.Sqrt(float64(x*x + y*y))

你直接将参数转换为 float64 类型。

在这种情况下:

var f = math.Sqrt(x*x + y*y)

你传递了一个 int 类型的参数,而实际需要的是 float64 类型。

在这种情况下:

var f = math.Sqrt(9 + 16)

编译器能够推断出类型,并为你传递 float64 类型的参数。

英文:

The math.Sqrt function signature:

func Sqrt(x float64) float64

requires that you pass float64

In this case:

var f float64 = math.Sqrt(float64(x*x + y*y))

You are converting to float64 directly

In this case:

var f = math.Sqrt(x*x + y*y)

you are passing an int, when float64 is required.

In this case:

var f = math.Sqrt(9 + 16)

The compiler is able to infer the type, and pass float64 for you.

答案2

得分: 4

当我们直接传递一个数字时,它会自动转换吗?

不,实际上并不会。你所说的"直接数字"在Go语言中被称为"常量",常量通常是"无类型"的,并且(几乎)具有任意精度。常量有特殊的规则:常量5和通过a := 5定义的整数a的行为不同,因为5是一个具有特殊规则的常量,而不是int类型。

9 + 16这样的常量表达式在编译时被计算,就像你输入了25一样。这个25仍然是一个常量。

虽然Go语言对于类型没有自动转换,但是它确实对常量到多种类型的转换进行了自动转换。常量25可以自动转换为float64、int、uint8甚至complex128。

请阅读博客文章https://blog.golang.org/constants和官方语言规范,以获得完整的解释和所有细节:https://golang.org/ref/spec#Constants。这篇文章比我能够更好地解释了"无类型整数"的奇怪概念。

*) "实际上并不会",因为用这种方式思考并不有帮助。在Go语言中,常量的区分是特殊的:大多数其他语言将3+5视为两个整数的和,结果为一个整数,而Go语言将其视为两个无类型整数常量,并将此表达式计算为一个新的任意精度、无类型的常量。只有在稍后才将常量转换为实际的整数。

英文:

> But when we pass a number directly, it automatically converted?

No, not really *). Your "direct numbers" are called "constants" in Go and constants are often "untyped" and (almost) of arbitrary precision. There are special rules for constants: A constant 5 and the integer a defined by a := 5 behave differently because 5 is a constant with special rules and not an int.

Constant expressions like 9 + 16 are evaluated at compile time like if you had typed 25. This 25 is still a (constant.

While Go does not have automatic type conversions for types it does have automatic conversions from constants to several types. The constant 25 can be converted to float64 or int, uint8 or even complex128 automatically.

Please read the blog post https://blog.golang.org/constants and the official language spec for a full explanation and all details: https://golang.org/ref/spec#Constants . This explains the strange notion of
"untyped integer" better than I could.

*) "not really" because it is not helpful to think about it that way. The distinction of constants is special in Go: Most other languages tread 3+5 as a sum of two ints resulting in an int while Go sees two untyped integer constants and evaluates this expression into a new arbitrary precision, untyped constant. Only later are constants converted to actual integers.

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

发表评论

匿名网友

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

确定