golang 是单进程的吗?

2023-10-17 13:55:56 +08:00
 chaleaochexist

我在一个 goroutine 修改环境变量, 想在其他所有 goroutine 中生效? 可以吗?

5882 次点击
所在节点    Go 编程语言
85 条回复
chaleaochexist
2023-10-17 21:06:33 +08:00
@kiripeng 大佬这是另一个问题了.
大佬能通俗易懂的解释一下 什么是 Happens-Before 吗?
chaleaochexist
2023-10-17 21:07:40 +08:00
@ygtq go 和 c++的区别是 go 有一个 goroutine 这个东西是由 runtime 控制的. 所以才上来确认一下.
通常来说确实应该是单进程.
aisk
2023-10-17 21:24:15 +08:00
@chaleaochexist 动手测试一分钟,群里讨论一整天。
chaleaochexist
2023-10-17 22:09:05 +08:00
@aisk 这个东西不能通过 demo 去验证.
当然了严谨一点说 可以证伪. 但是不能验证正确.

譬如 runtime 有一种机制, 当 goroutine < 5. 或者换个说法 count(runtime) < 5 是单进程, >=5 是多进程模式.
所以我发帖上来问问, 不知道为什么楼上一堆冷嘲热讽.
standchan
2023-10-17 22:16:34 +08:00
我没有找到你说的 golang runtime 当协程数量大于一定数目就变成了多进程模式。你在哪里看到的资料能发出来看一下吗?我认为多进程肯定不合理,进程之间的通信要比协程之间的通信复杂太多了,还涉及到了各种同步等等乱七八糟的。另外,你起初问的问题确实特别让人费解,标题和正文我找不到逻辑的相关性
standchan
2023-10-17 22:26:03 +08:00
另外 runtime 对 goroutine 的控制也是基于系统进程里面进行的。它是在进程下面的,当然 exec 会生成新的进程,但生成的进程和 golang 程序所在的进程完全没关系。runtime 也不可能凌驾于进程们之上去管理多个进程。go 是面向云原生高并发,如果是你说的多进程模式,那延迟会高很多很多。
aisk
2023-10-17 22:26:19 +08:00
@chaleaochexist 错的不是你。
chaleaochexist
2023-10-17 22:54:40 +08:00
@standchan 当协程数量大于一定数目就变成了多进程模式.
这个是我脑补的.

我其实也倾向于是单进程.

只不过上来发帖确认一下.
standchan
2023-10-17 23:52:25 +08:00
@chaleaochexist #68 嗯嗯,那现在应该知道结果了就行了。另外,问题的描述可以再提升一下,看起来真的会让人有点懵。
voidmnwzp
2023-10-18 00:05:03 +08:00
…你告我哪个语言不是单进程的
qwq11
2023-10-18 01:13:28 +08:00
op 去看下操作系统,环境变量是在进程启动的时候被 OS 压到程序的栈里的,所以说是静态的,而不是动态读取。如果你说的是在同一进程下的 goroutine ,显然不会生效,如果你说的是不同进程的 goroutine ,并且在修改完了之后才启动新进程,那答案是会生效

你在 #30 说的情况,答案是不会生效
chaleaochexist
2023-10-18 02:27:34 +08:00
@qwq11 啊??
什么?
```
package main

import (
"fmt"
"os"
"time"
)

func main() {
os.Setenv("FOO", "1")
fmt.Println(os.Getenv("FOO"))
go func() {
os.Setenv("FOO", "2")
}()
time.Sleep(1 * time.Second)
fmt.Println(os.Getenv("FOO"))
}
```
CrazyMonkeyV
2023-10-18 08:42:00 +08:00
@chaleaochexist 前面我觉得你菜就算了,谁没菜过?看到后面有点逆天。程序员不是自己搞 demo 来证明,靠不明需求的论坛? 6666
Masoud2023
2023-10-18 09:34:42 +08:00
@chaleaochexist #72

好奇你以前是做什么语言的。这种拿环境变量共享内存的方法我还是第一次见到。

go 的话共享内存应该用 channel ?
bler
2023-10-18 09:35:38 +08:00
@bler 我更新一下我的回答,”pipeline 的类变量在两个爬虫中会共用“,这是错误的,虽然两个爬虫在同一进程中,但是两个爬虫类变量是隔离的
chaleaochexist
2023-10-18 10:08:15 +08:00
@Masoud2023 因为我 B 了一些人不知道你说的 72 楼是哪个.

也不算共享内存吧.
就是在不停机的情况下 动态切换 kafka 的配置.
且 if flag == 1 then 从环境变量读配置
else 从数据库读配置.

那我之前的想法是当从数据库读配置之后, 写到环境变量中, 这样其他代码就不用动了.
然后就发帖问问题了.

说得通吗?
pkoukk
2023-10-18 10:34:16 +08:00
@chaleaochexist #76
有这种需求,一般我们会搞个 etcd ,redis 也行啊。
你这个玩法让人真是搞不懂,线上部署的时候直接跑二进制,不用 docker ?
不用 docker 隔离环境罢了,还用环境变量,这么信任跑在这台机器上的其它服务?
说到进程问题,我用过的语言里,只要你不 fork ,它们就是共用完全相同的上下文和内存,别管他在 cpu 里有几个实例,那是 os 的事情,和语言无关。
qwq11
2023-10-18 10:44:19 +08:00
@chaleaochexist #72 你是对的,去研究了下 linux 确实可以修改本进程的环境变量,修改之后 OS 会重新给进程分配环境变量表,这点有点出乎意料
#76 的需求建议用变量存,把 os.Getenv 换成 KafkaConfigProvisioner.GetConfig 也用不了多少时间,比你发帖回帖快,用环境变量还得上信号量或者读写锁
chaleaochexist
2023-10-18 10:49:38 +08:00
@pkoukk
你说的是类似 zookeeper 的监听与推送吧?

是 docker 里的环境变量. 为什么提到环境变量就一定是裸机的呢? docker 不能有环境变量吗?
无论是推还是拉 都需要网络开销. 本地读取环境变量对于小项目来说就是最佳方式. 搞那么做组件做什么?

不知道是谁的问题, 这个楼里全都是反问和嘲讽. 不知道是我的问题还是怎么回事.
==========================================
以下我想回复你的第一个版本.
@pkoukk

是 docker 里的环境变量.

你说的是类似 zookeeper 的监听与推送吧?

小项目 一开始设计的时候就没那么复杂.
chaleaochexist
2023-10-18 10:50:46 +08:00
@qwq11 是的.我最后是用 viper 解决的.
实际上, 我发帖的时候, 问题已经解决了.

这就是一个很单纯的问题. 也许在很多人看来很 SB.
但是我现在是有点困惑为什么一开始嘲讽的人那么多.

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/982738

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX