zoukankan      html  css  js  c++  java
  • go语言中的并发

    package main;
    
    import (
    	"fmt"
    	"runtime"
    	"sync"
    )
    
    //goruntine奉行通过通信来共享内存,而不是共享内存来通信
    //channel是goruntine沟通的桥梁,大都是阻塞同步的
    //通过make创建,close关闭
    //channel是引用类型
    //使用for range来迭代操作channel
    //可设置单向或双向通道
    //可设置缓存大小,在未被填满前不会发生阻塞
    
    func main() {
    	//这里需要设置chan的类型
    	ch := make(chan bool);
    	go func() {
    		fmt.Println("run...");
    		ch <- true;
    	}();
    	//这里是阻塞的,等到匿名函数执行完成,给ch设置为true时
    	//这里能读取出数据时,就退出。
    	<-ch;
    
    	ch1 := make(chan bool);
    	go func() {
    		fmt.Println("run...");
    		ch1 <- true;
    		close(ch1);
    	}();
    	//对chan进行迭代操作时,必须在某个地方关闭该chan,不然会发生死锁
    	for v := range ch1 {
    		fmt.Println(v);
    	}
    
    	//有缓存是异步的
    	ch2 := make(chan bool, 1);
    	go func() {
    		fmt.Println("run...");
    		<-ch2;
    	}();
    	ch2 <- true;
    
    	//使用多核
    	runtime.GOMAXPROCS(runtime.NumCPU());
    	ch3 := make(chan bool, 10);
    	for i := 0; i < 10; i++ {
    		go run(ch3, i);
    	}
    	//这里读取10次,跟上面go run()执行次数相同
    	//保证10次运行都执行完,才退出
    	for i:= 0; i < 10; i++ {
    		<-ch3;
    	}
    
    	//这里创建任务
    	wg := sync.WaitGroup{};
    	wg.Add(10);
    	for i := 0; i < 10; i++ {
    		go run2(&wg, i);
    	}
    	//等待所有任务完成
    	wg.Wait();
    
    	//有多个chan时,如何处理
    	ch4, ch5 := make(chan int), make(chan string);
    	//用于判断是否关闭
    	ch6 := make(chan bool);
    	go func() {
    		for {
    			select {
    			case v, ok := <-ch4:
    				if !ok {
    					ch6 <- true;
    					break;
    				}
    				fmt.Println(v);
    			case v, ok := <-ch5:
    				if !ok {
    					ch6 <- true;
    					break;
    				}
    				fmt.Println(v);
    			}
    		}
    	}();
    
    	ch4 <- 1;
    	ch4 <- 2;
    	ch5 <- "hello";
    	ch5 <- "world";
    
    	close(ch4);
    	close(ch5);
    	//循环读取二次
    	for i := 0; i < 2; i++ {
    		<-ch6;
    	}
    
    }
    
    func run(ch chan bool, ix int) {
    	a := 0;
    	for i := 1; i < 10000; i++ {
    		a += i;
    	}
    	fmt.Println(ix, a);
    
    	//给chan传递true,说明该run执行结束
    	ch <- true;
    }
    
    func run2(wg *sync.WaitGroup, ix int) {
    	a := 0;
    	for i := 1; i < 10000; i++ {
    		a += i;
    	}
    	fmt.Println(ix, a);
    	//任务完成
    	wg.Done();
    }
    

      

  • 相关阅读:
    线性表之顺序表的结构与实现
    (转)面试题1:第一个只出现一次的字符
    c++ 虚基类应用
    c++ 多重继承
    c++ 单继承派生类的构造函数
    c++ 构造函数
    深入 Struts2 的配置
    c++ 结构体
    深入浅出C指针
    HTML5 小实例
  • 原文地址:https://www.cnblogs.com/jkko123/p/6820352.html
Copyright © 2011-2022 走看看