Although the go compiler produces local executable code, the code is still running on the Go runtime (this part of the code can be found in the runtime package). This runtime is similar to the virtual machine used by the Java and. NET languages, and it manages to include memory allocations, garbage collection (section 10.8), stack processing, goroutine, channel, slice (slice), Map and reflection (reflection), and so on.
runtime
The scheduler is a very useful thing about packages in runtime
several ways:
gosched: Let the current thread make cpu
up for another thread to run, it will not suspend the current thread, so the current thread will continue to execute in the future
numcpu: Returns the number of cores in the current system CPU
Gomaxprocs: Sets the maximum number of simultaneous cores that can be used CPU
goexit: Exit current goroutine
(but defer
statement will execute as usual)
numgoroutine: Returns the total number of tasks being executed and queued
GOOS: Target operating system
Numcpu
package mainimport ( "fmt" "runtime")func main() { fmt.Println("cpus:", runtime.NumCPU()) fmt.Println("goroot:", runtime.GOROOT()) fmt.Println("archive:", runtime.GOOS)}
Operation Result:
Image.png
Gomaxprocs
Golang
By default, all tasks are run in one cpu
core, and if you want to goroutine
use multicore in, you can use runtime.GOMAXPROCS
function modification to use the default value when the parameter is less than 1.
package mainimport ( "fmt" "runtime")func init() { runtime.GOMAXPROCS(1)}func main() { // 任务逻辑...}
Gosched
The purpose of this function is to let the current yield goroutine
CPU
, when one is goroutine
blocked, Go
will automatically goroutine
transfer the other to the same system thread to goroutine
another system thread, so that these goroutine
do not block.
Note the method used to close the channel close()
.
Extended thinking: Close () closes the channel, if close a closed channel, will be an error. How do we determine the state of the channel at this point when we close it?
Here is an article you can refer to the following
https://www.jianshu.com/p/d24dfbb33781
package mainimport ( "fmt" "runtime")func init() { runtime.GOMAXPROCS(1) //使用单核}func main() { exit := make(chan int) go func() { defer close(exit) go func() { fmt.Println("b") }() }() for i := 0; i < 4; i++ { fmt.Println("a:", i) if i == 1 { runtime.Gosched() //切换任务 } } <-exit}
Results:
Image.png
Using multi-core testing:
package mainimport ( "fmt" "runtime")func init() { runtime.GOMAXPROCS(4) //使用多核}func main() { exit := make(chan int) go func() { defer close(exit) go func() { fmt.Println("b") }() }() for i := 0; i < 4; i++ { fmt.Println("a:", i) if i == 1 { runtime.Gosched() //切换任务 } } <-exit}
Results:
Image.png
Depending on your machine to set the runtime's number of cores, but the result is not necessarily the same as above, or at the main
end of the function with select{} to let the program block, the result is as follows:
Image.png
Multicore comparisons are suitable for that CPU
intensive program, and if IO
intensive use of multicore increases CPU
the cost of switching.
Gosched to explain again
Gosched the time slice used to make up the CPU. Like a relay race, a run for a while runtime.Gosched()
, will give the time slice to B, let B run.
package mainimport ( "runtime" "fmt")func init() { runtime.GOMAXPROCS(1)}func say(s string){ for i := 0; i < 2; i++ { runtime.Gosched() fmt.Println(s) }}func main() { go say("world") say("hello")}
Output Result:
Hello
World
Hello
Note the results:
1, the first output of Hello, after the output of the world.
2, hello output 2, World output 1 (because the 2nd Hello output, the main thread exited, the 2nd world did not have a chance)
Put the runtime in the code. Gosched () is commented out and the result is:
Hello
Hello
Because say ("hello") This sentence takes up time, when it executes, the thread ends, and say ("World") has no chance.
As you can see here, the goroutins in Go is not running at the same time. In fact, if you do not pass in the code
Runtime. Gomaxprocs (n) where n is an integer,
Specifies the use of multicore, Goroutins are in a line thread, between them through the continuous letting out the time slices in turn to run, to achieve similar simultaneous effect.