Go 常量为什么只支持基本数据类型?

Unity实时控制佳能单反拍照全流程(附EDSDK 3.6.1配置避坑指南) 本文详细介绍了在Unity中实时控制佳能单反相机进行拍照的完整流程,重点提供了EDSDK 3.6.1的配置与避坑指南。内容涵盖从SDK获取、环境搭建、相机初始化、参数设置到实现拍照控制,并深入探讨了实时取景的延迟优化方案与资源管理,旨在帮助开发者高效集成专业相机,提升AR/VR及摄影测量等应用的视觉输入质量。 阅读详情

大家好,我是煎鱼。

相信大家在接触 Go 这门编程语言时,就会学到常量这个知识点。

各大编程语言会教你,常量是不可变变量的一种类型。只要定义了常量,你就可以安心的用他。不用担心值在哪里就被程序莫名奇妙的给改了。

常量的使用例子

如下例子:

const s string = "脑子进煎鱼了"

func main() {
 fmt.Println(s)

 const n = 500000000

 const d = 3e20 / n
 fmt.Println(d)

 fmt.Println(int64(d))

 fmt.Println(math.Sin(n))
}

输出结果:

脑子进煎鱼了
6e+11
600000000000
-0.28470407323754404

你可能会发现一个奇怪的点。那就是例子里都是基本的数据类型。那能不能用复杂点的数据类型呢,例如 Go 里比较经典的切片。

如果是用 var 声明:

var s = []string{"摸", "煎", "鱼"}

func main() {
 fmt.Println(s)
}

正常输出:[摸 煎 鱼]

如果是用 const 声明:

const s = []string{"摸", "煎", "鱼"}

将会报错:

./prog.go:7:11: []string{…} (value of type []string) is not constant

因为在 Go 中,仅支持字符、字符串、布尔和数值类型的常量。这和其他编程语言间多多少少还是有点不一样的。

为什么不支持更多类型

为什么在 Go 中常量只支持这几种基础类型,为什么没法支持复杂类型,或是所有类型?

这是非常 “奇怪” 的。毕竟 PHP 都能支持:

class MyClass
{

    const ABC = array('A', 'B', 'C');

    const A = '1';

    const B = '2';

    const C = '3';

    const NUMBERS = array(
        self::A,
        self::B,
        self::C,
    );

}

这又是出于什么缘由?

已有 10 年老提案

我认真翻阅了 Go issues 等相关资料,终于发现竟然在 2013 年(10 年前),就已经有人提出过这个提案:

28e111623aecd705363d752503a36ee4.png

提出者 @RickySeltzer,认为:

var each1 = []byte{'e', 'a', 'c', 'h'}

可以正常运行。

const each2 = []byte{'e', 'a', 'c', 'h'}

不行,直接报错:prog.go:7: const initializer []byte literal is not a constant

他认为这就是 Go 语言规范和设计上的缺陷,得改,得支持!

拒绝的论据是什么

对此也有各种争论,老大哥 @Robert Griesemer,10 年前已 在为 Go 贡献,现在依然还在...他对 Go 常量只支持基本类型这个设计给出了定论。

基于如下原因:

  • 首先这不是语言的缺陷,也不是设计的缺陷。Go 语言的常量是故意设计成只支持基本类型。

  • 基本类型到复杂类型的改变,这种变化的影响比我们看到的要深远得多。需要考虑很多问题。

    • 常量 channel、常量指针、常量 maps、常量 slice 都要支持吗?

    • 先支持常量 array 和 常量 struct?

    • 要支持到什么程度,以什么来作为标准决定?

  • 设计上,Go 团队期望类型系统(包括常量的含义)相对简单,以免在编译时出现问题。

    • 常量更多类型的支持,会增加复杂性。不清楚这样做的好处是否值得(ROI)。

    • 常量是否可以寻址?const 数组的元素本身必须是 const 吗?

汇总一下,潜台词就是:

  1. 设计如下:常量只支持基本类型,是 Go 设计上就是这么决定的。

  2. ROI 要衡量一下:没有支持更多的复杂类型,是认为好处不多。也没有想清楚这块的缘由。

  3. 少即是多:类型系统要保持少即是多(less is more)。

实战中的骚操作

在相关提案的 issues 中看到欧神(@Changkun Ou)也参与了讨论,他例举了一个常量的经典骚操作。

代码如下:

- const ErrVerification = errors.New("crypto/rsa: verification error")
+ var ErrVerification = errors.New("crypto/rsa: verification error")

在对应的 Go 工程中可能是这么使用:

import "cropto/rsa"
func init() {
 rsa.ErrVerification = nil
}

这个场景我还真见过,一开始想定义 const,结果不支持。只能被迫 var。这不,就开天窗了。

总结

Go 核心团队在综合衡量 ROI 后,认为常量支持更多的类型在可预见的未来不会改变。因为将常量的概念扩展到基本类型之外将是一个重大变化,会产生各种影响。

在此刻(Go1)改变语言的门槛非常高,需要有明确的定义,要有完整的提案以及对成本和效益等的详细分析。

如果出现,只可能在未来的 Go2。但结合 rsc 最新的结论,没有 Go2 的话,那如果未来真的做,那就是通过 GODEBUG 和 go.mod 的 go 版本号来实现了。

常量更多类型的支持,虽然已经提出了 10 年。但目前 Go 核心团队推进乏力,想必,可能还要个 5 年吧。

推荐阅读

关注和加煎鱼微信,

一手消息和知识,拉你进技术交流群👇

100b32168d09b15b9c01be546fcd2e60.jpeg

b750269e890ba4cc39301b076bf9a184.png

你好,我是煎鱼,出版过 Go 畅销书《Go 语言编程之旅》,再到获得 GOP(Go 领域最有观点专家)荣誉,点击蓝字查看我的出书之路

日常分享高质量文章,输出 Go 面试、工作经验、架构设计,加微信拉读者交流群,和大家交流!

GoGo语言中的基本数据类型与类型转换 Go语言是一种静态类型、编译型语言,它提供了丰富的数据类型用于处理各种数据。 在Go中,数据类型主要分为两大类:基本数据类型和派生数据类型。值类型包括整型、浮点型、布尔型、字符串等,而派生数据类型则包括指针、数组、结构体、函数、切片、映射、通道和接口等。本文将通过实际案例详细讲解Go语言中的基本数据类型及其用法。 阅读详情

相关推荐

go从入门到精通】go基本类型和运算符用法

大家好,这是我给大家准备的新的一期专栏,专门讲golang,从入门到精通各种框架和中间件,工具类库,希望对go有兴趣的同学可以订阅此专栏。上一篇文章中偏重概念和知识,想必大家都对如何开始写代码已经开始蠢蠢欲动了,但是不要着急,基础知识扎实,能让你走很弯道。

yolo模型训练找我,AI游戏合作找我 8万+

Go 设计哲学:即是,哪里来的?

大家好,我是煎鱼。之前在 Go 社区分享知识和经验时,经常会听见诸如:less is more、即是,大道至简、大道不停地至简等黑话。甚至讨论 Go issues 和提案时,都会有人用...

EDDYCJY的博客 1063

Unreal 从入门到进阶 之 如何实现Pixel Streaming

Unreal Engine 5 (UE5) 的 Pixel Streaming 是一项基于云端的实时流媒体技术,允许将 UE5 应用的高质量图形渲染结果通过 WebRTC 协议传输到用户的浏览器或轻量级设备,同时将用户输入(如鼠标、键盘、触控)回传到服务器处理。UE的插件相对比较好用,但是就是环境下载总是失败。希望这篇文章对你有所帮助。

TxNet 1325

Go语言--编程哲学

1 Go语言设计哲学 1.1 即是 Go语言没有犯C++的错误,没有过度地追求语言特性的大而全,而是最大限度地控制语言特性的数量,控制语言使用的复杂性。二八定律在编程语言中可以描述为80%的代码仅使用20%的语言特性。增加语言特性并不能开发效率的提升,原因是它会增加复杂性,导致使用者更容易犯错;有些复杂的语言特性可以通过库的其他形式来辅助支持。所以,在Go语言中,没有看到运算符重载,没有看到重继承等不太实用的语言特性。 即是还隐含另一个概念就是语言特性的正交性。几何上的正交指的是两个向量的垂

yunfan 802

Go 常量支持基本数据类型为什么?社区撕了 9 年了...

大家好,我是煎鱼。今天给大家分享的一个提案,已经在 Go 社区讨论了整整 9 年(2013~2022),它与我们的日常编程密切相关。今天就由煎鱼和大家一起深入学习和了解提案《proposal: spec: allow constants of arbitrary data structure type[1]》吧,看看有没有什么新的想法。背景我们先看看以下示例代码,如下:p...

EDDYCJY的博客 585

Golang 基本数据类型

Golang 基本数据类型 golang 是一种强类型语言,变量使用时需要进行强制类型定义,一旦某一个变量被定义类型,如果不经强制转换,那么它永远就是该数据类型。本文主要介绍 golang基本数据类型。 变量声明及初始化 go 语言推荐使用驼峰式命名,如 QuoteRuneToASCII 和 parseRequestLine 等。 定义变量的几种形式 // 第一种,先声明类型,再进行初始化赋值 // 如果没有初始化,则变量默认为零值。 var a int a = 3 // 第二种, 根据赋值自动适配类

wallace_www的博客 1万+

golang语法学习(一):变量,常量以及数据类型

学习一门新的语言肯定是要从他的基本语法开始,语法构成了整个程序设计的基础,从语法中我们也可以看到这门语言的一些特性,但是话说回来,语法这东西,不同的语言大同小异,所以这也对语法的记忆造成了一定的难度,其实最好的方法应该是旁边有本书,随时可以拿过来查阅或者纠正。当然golang的语法也是这样,下面的一些是我学习七牛团队许式伟等出的《Go语言编程》: http://baike.baidu.com/li

挑灯看剑的专栏 7257

Golang 基础语法、常量、变量、数据类型

目录.go文件基本结构变量常量数据类型内建数据类型指针 Pointer结构体接口接口的定义和实现任何类型接口的组合内建容器数组 Array切片 Slice集合 Map类型转换类型扩展   Go,又称Golang,是google开源的编程语言,原生支持并发编程 没有对象的概念,不支持继承、态,没有泛型、try…catch 有接口、函数式编程、csp并发模型(goroutine+channel)   .go文件基本结构 /* 一个包可以对应个目录,一个目录只能对应一个包,同一目录下包

chy-x 的博客 1397

Golang】认识Go语言基本数据类型

我们不论在学习什么语言中,我们都要去认识一下这个语言中的数据类型,当然学习Go也不例外,我们也要去认识一下其相关的数据类型,当然这些数据类型基本上是大同小异的,如果学之前一些语言的学习经验的话,在理解学习起来将会更加的迅速。

感谢您的关注! 1208

Golang】语法基础——深入解析Go语言数据类型

Go语言(简称Golang)作为一门现代编程语言,以其简洁、强大的特性备受开发者青睐。在实际开发中,数据类型语言的核心部分,理解和正确使用数据类型是编写高效、健壮代码的基础。本文将详细介绍Go语言中的基本数据类型及其特性,帮助读者更好地掌握Go语言的使用。

Linke的博客 1980

go语言】2.1.1 变量,常量数据类型

Go 语言中,变量是存储数据的基本单位,常量则是固定不变的数据。每个变量和常量都有其对应的数据类型

Andy0214的专栏 5447

Go 语言常量

什么是常量常量Go 语言中表示固定值的标识符,在程序运行期间不可更改。常量的类型仅限于布尔型、数字型(整数、浮点数、复数)和字符串型。如何定义常量?使用const,如。隐式类型:省略类型,编译器自动推断,如。常量的作用域常量可以定义在包级(全局)或函数内,编译时确定其值。特殊特性常量不能使用运算符获取地址。常量存储在数据区的常量区,变量则存储在栈区或堆区。开发中常使用全大写命名(如LENGTH)以区分变量。枚举与iota。

likuoelie的博客 840

go基本数据类型、变量、常量

标识符 例如变量名、常量名、函数名等等。 Go语言中标识符由字母数字和_(下划线)组成,并且只能以字母和_开头。例如abc,_ ,_123,a123。 基本数据类型 Go语言中有丰富的数据类型,除了基本的整型、浮点型、复数、布尔型、字符串、byte、rune外,还有数组、切片、结构体、函数、map、通道(channel)等。 这些类型都在builtin.go文件中,这个包含go的预声明定义包含常用的各种类型和方法声明,包括变量和常量两部分,大家可以自己查阅一下。 整型 有符号(带正负的)整型:int8(0-

HongHu-ing的博客 576

Golang——2、基本数据类型和运算符

Go语言数据类型分为基本类型和复合类型。基本类型包括整型(int8/int16/int32/int64及无符号版本)、浮点型(float32/float64)、布尔型(bool)和字符串(string)。文章通过代码示例演示了各类型的使用方法,包括类型转换、数字字面量语法、浮点数精度问题、布尔型特性以及字符串操作(拼接、分割、索引等)。特别指出浮点数运算存在精度损失问题,建议使用第三方库解决;字符串采用UTF-8编码,支持行反引号语法和丰富的内置操作方法。

Talon的博客 1583

Go——运算符,变量和常量基本类型

相对于变量,常量是恒定不变的值,用于定义程序运行期间不会改变的值。常量的声明和变量声明非常相似,只是把var换成const,常量在定义的时候必须赋值。声明了pi和e这两个变量之后,在整个程序运行期间它们的值都不能再发生变化了。const (e = 2.7182const同时声明常量时,如果省略了值则表示和上一行的值相同。//n1,n2,n3的值都是100const (n1 = 100n2n3Golang更明确的数字类型命名,支持Unicode,支持常用数据结构。

weixin_57023347的博客 1499

Go-2】基本语法与数据类型

Map是键值对的无序集合,键和值可以是不同的类型。本章将深入介绍Go基本语法和数据类型,帮助你建立扎实的编程基础。切片由指向数组的指针、长度和容量组成。在Go中,不同类型之间的转换需要显式进行,称为类型转换。Go中使用指针可以提高程序的性能,避免大量数据的复制。复合类型是由基本类型组成的类型,包括数组、切片、Map、结构体和指针。Go支持种整型,包括有符号和无符号类型,以及不同位数的类型。结构体是由个字段组成的复合数据类型,可以包含不同类型的数据。函数是程序的入口点,定义了程序启动时执行的代码。

2202_75331338的博客 1226

3、做中学 | 二年级上期 Golang数据类型常量/变量声明使用

本文介绍了Go语言基本数据类型常量和变量的定义与使用方法。主要内容包括: 基本数据类型:详细列举了布尔型、整数型(int/uint系列)、浮点型、复数型、字符串型等Go语言的基础数据类型,包括每种类型的取值范围、零值和示例。 常量:介绍了常量的定义语法(使用const关键字),强调常量的不可修改特性,并展示了显式/隐式声明方式以及常量简写形式。 变量:通过类比药材柜形象说明变量概念,详细讲解三种变量声明方式(先声明后赋值、声明时赋值、简短声明),以及变量同时声明的方法。 全文以代码示例和表格形式清晰

liu_dongdong55的博客 1128

【从零开始学习Go语言】九.Go语言之变量常量及指针总结

【从零开始学习Go语言】九.Go语言之变量和常量一.变量1.1 显示的完整声明1.2 简短声明二.常量三.基础类型四. 指针4.1定义4.2 用途五.总结 一.变量 变量是通过一个名称绑定一块内存地址,该内存地址所存储的数据类型由定义变量时指定,该内存的地址数据可以被改变;变量声明的方法有种 1.1 显示的完整声明 package main import "fmt" func main...

一只特立独行的兔先森 1万+

GoGo语言数据类型

Go语言数据类型介绍

weixin_44211968的博客 3804

MATLAB2020提取复杂背景苹果轮廓实例

具体视频教程见https://www.bilibili.com/video/BV1dz4y1Q7Kf/

上一篇: 合订本|用Go语言实现 23 种设计模式及学习重点
下一篇: Go 官方新玩具:漏洞管理和扫描,看看自己项目有没有坑?
煎鱼(EDDYCJY)
博客等级 码龄12年 1818粉丝 · 505原创
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值