<?xml version="1.0" encoding="UTF-8" ?>
<rss version="2.0">
<channel>
<title><![CDATA[向东博客 专注WEB应用 构架之美 --- 构架之美，在于尽态极妍 | 应用之美，在于药到病除]]></title> 
<link>http://jackxiang.com/index.php</link> 
<description><![CDATA[赢在IT，Playin' with IT,Focus on Killer Application,Marketing Meets Technology.]]></description> 
<language>zh-cn</language> 
<copyright><![CDATA[向东博客 专注WEB应用 构架之美 --- 构架之美，在于尽态极妍 | 应用之美，在于药到病除]]></copyright>
<item>
<link>http://jackxiang.com/post//</link>
<title><![CDATA[[实践OK]关于go进行多进程通讯的等待子进程问题学习浅显研究。]]></title> 
<author>jack &lt;xdy108@126.com&gt;</author>
<category><![CDATA[Php/Js/Shell/Go]]></category>
<pubDate>Mon, 04 Jan 2021 10:53:29 +0000</pubDate> 
<guid>http://jackxiang.com/post//</guid> 
<description>
<![CDATA[ 
	背景：有一篇朋友圈说是一个k8s里面Server的Pod销毁上报Zookeeper出现IP地址连接还是原来的，用到了zk的watcher，理论上不应该这样，于是查来查去，其大体意思就是说用了Go的多进程，有一个进程去读取配置了，因为配置还是老的，而用到了Go的多进程，于是文末那代码，我看了下，简单，但不明白，于是顺藤摸瓜学习一下这个rsync的原理。<br/><br/><br/>——————————<br/>#tree&nbsp;&nbsp;-L 2 .&#124;grep go<br/>├── loop.go<br/>├── pipe.go<br/>├── waitgrouppointer.go<br/>└── wg.go<br/><br/><br/>#cat loop.go <br/>package main<br/><br/>import (<br/>&nbsp;&nbsp;&nbsp;&nbsp;&quot;fmt&quot;<br/>&nbsp;&nbsp;&nbsp;&nbsp;//&quot;time&quot;<br/>)<br/><br/>func main()&#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;for i := 0; i &lt; 100 ; i++&#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;go fmt.Println(i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/>&nbsp;&nbsp;&nbsp;&nbsp;//time.Sleep(time.Second)<br/>&#125;<br/><br/>这个说是运行太快，子进程没输出主进程就退了，啥也不输出。<br/><br/><br/><br/>#cat pipe.go <br/>package main<br/><br/>import (<br/>&nbsp;&nbsp;&nbsp;&nbsp;&quot;fmt&quot;<br/>&nbsp;&nbsp;&nbsp;&nbsp;//&quot;time&quot;<br/>)<br/>func main() &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;c := make(chan bool, 100)<br/>&nbsp;&nbsp;&nbsp;&nbsp;for i := 0; i &lt; 100; i++ &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;go func(i int) &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fmt.Println(i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;c &lt;- true<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&#125;(i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/><br/>&nbsp;&nbsp;&nbsp;&nbsp;for i := 0; i &lt; 100; i++ &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;-c<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/>&#125;<br/><br/>这个说是管道要是上万，会耗尽系统管道资源。<br/><br/><br/>#cat waitgroup.go&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<br/>package main<br/><br/>import (<br/>&nbsp;&nbsp;&nbsp;&nbsp;&quot;fmt&quot;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&quot;sync&quot;<br/>&nbsp;&nbsp;&nbsp;&nbsp;//&quot;time&quot;<br/>)<br/>func main() &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg := sync.WaitGroup&#123;&#125;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg.Add(100)<br/>&nbsp;&nbsp;&nbsp;&nbsp;for i := 0; i &lt; 100; i++ &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;go func(i int) &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fmt.Println(i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;wg.Done()<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&#125;(i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg.Wait()<br/>&#125;<br/><br/><br/>这个说是挺好的，因为它用到了原子加减法，这里好像C语言也有类似的函数，<br/><br/><br/><br/>再就是说它是用来阻塞方进程的，WaitGroup 对象内部有一个计数器，最初从0开始，它有三个方法：Add(), Done(), Wait() 用来控制计数器的数量。Add(n) 把计数器设置为n ，Done() 每次把计数器-1 ，wait() 会阻塞代码的运行，直到计数器地值减为0。<br/><br/>这里首先把wg 计数设置为100， 每个for循环运行完毕都把计数器减一，主函数中使用Wait() 一直阻塞，直到wg为零——也就是所有的100个for循环都运行完毕。相对于使用管道来说，WaitGroup 轻巧了许多。<br/><br/><br/>最后，如果要搞裂成函数，得用引用传入，指针变量：<br/>WaitGroup对象不是一个引用类型<br/>WaitGroup对象不是一个引用类型，在通过函数传值的时候需要使用地址：<br/><br/>#cat waitgrouppointer.go <br/>package main<br/><br/>import (<br/>&nbsp;&nbsp;&nbsp;&nbsp;&quot;fmt&quot;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&quot;sync&quot;<br/>&nbsp;&nbsp;&nbsp;&nbsp;//&quot;time&quot;<br/>)<br/>func main() &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg := sync.WaitGroup&#123;&#125;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg.Add(100)<br/>&nbsp;&nbsp;&nbsp;&nbsp;for i := 0; i &lt; 100; i++ &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;go f(i, &amp;wg)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg.Wait()<br/>&#125;<br/><br/>// 一定要通过指针传值，不然进程会进入死锁状态<br/>func f(i int, wg *sync.WaitGroup) &#123; <br/>&nbsp;&nbsp;&nbsp;&nbsp;fmt.Println(i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg.Done()<br/>&#125;<br/><br/><br/>以上来自：https://blog.csdn.net/u013474436/article/details/88749749<br/><br/>溯源来自：https://mp.weixin.qq.com/s/s9G6yDqfeFepbKT6DJASng<br/><br/><br/><br/>#cat wg.go <br/>package main<br/><br/><br/>import (<br/>&nbsp;&nbsp;&quot;fmt&quot;<br/>&nbsp;&nbsp;&quot;sync&quot;<br/>)<br/><br/><br/>func main() &#123;<br/>&nbsp;&nbsp;ok := true<br/>&nbsp;&nbsp;for i := 0; i &lt;1000; i ++ &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;var arr []int<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg := sync.WaitGroup&#123;&#125;<br/><br/><br/>&nbsp;&nbsp;&nbsp;&nbsp;for j := 0; j &lt;2; j ++ &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;wg.Add(1)<br/><br/><br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;go func() &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;defer wg.Done()<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;arr = append(arr, i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&#125;()<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/>&nbsp;&nbsp;&nbsp;&nbsp;wg.Wait()<br/><br/><br/>&nbsp;&nbsp;&nbsp;&nbsp;if len(arr) &lt; 2 &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fmt.Printf(&quot;error:%d &#92;n&quot;, i)<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ok = false<br/>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;break<br/>&nbsp;&nbsp;&nbsp;&nbsp;&#125;<br/>&nbsp;&nbsp;&#125;<br/><br/><br/>&nbsp;&nbsp;if ok &#123;<br/>&nbsp;&nbsp;&nbsp;&nbsp;fmt.Println(&quot;ok&quot;)<br/>&nbsp;&nbsp;&#125;<br/>&#125;<br/><br/><br/>判断 key 是否在 map 中<br/>var nameList = map[string]string&#123;&quot;姓名&quot;: &quot;李四&quot;, &quot;性别&quot;: &quot;男&quot;&#125;<br/>name, ok := nameList[&quot;姓名&quot;] // 假如 key 存在，则 ok = true，否则，ok = false<br/>if ok &#123;<br/>&nbsp;&nbsp;fmt.Println(name)<br/><br/>来自：https://blog.csdn.net/weixin_38168322/article/details/99948042?utm_medium=distribute.pc_relevant.none-task-blog-BlogCommendFromBaidu-1.control&amp;depth_1-utm_source=distribute.pc_relevant.none-task-blog-BlogCommendFromBaidu-1.control
]]>
</description>
</item><item>
<link>http://jackxiang.com/post//#blogcomment</link>
<title><![CDATA[[评论] [实践OK]关于go进行多进程通讯的等待子进程问题学习浅显研究。]]></title> 
<author> &lt;user@domain.com&gt;</author>
<category><![CDATA[评论]]></category>
<pubDate>Thu, 01 Jan 1970 00:00:00 +0000</pubDate> 
<guid>http://jackxiang.com/post//#blogcomment</guid> 
<description>
<![CDATA[ 
	
]]>
</description>
</item>
</channel>
</rss>