2011-06-04 23 views
8

Estoy probando este código ir en mi Ubuntu VirtualBoxed 11,4¿Por qué la sentencia go no se ejecuta en paralelo?

package main 

import ("fmt";"time";"big") 
var c chan *big.Int 

func sum(start,stop,step int64) { 
    bigStop := big.NewInt(stop) 
    bigStep := big.NewInt(step) 
    bigSum := big.NewInt(0) 
    for i := big.NewInt(start);i.Cmp(bigStop)<0 ;i.Add(i,bigStep){ 
     bigSum.Add(bigSum,i) 
    } 
    c<-bigSum   
} 

func main() { 
    s := big.NewInt(0) 
    n := time.Nanoseconds() 

    step := int64(4) 
    c = make(chan *big.Int , int(step)) 
    stop := int64(100000000) 
    for j:=int64(0);j<step;j++{ 
     go sum(j,stop,step)  
    } 
    for j:=int64(0);j<step;j++{ 
     s.Add(s,<-c) 
    } 
    n = time.Nanoseconds() - n 
    fmt.Println(s,float64(n)/1000000000.) 
} 

Ubuntu tiene acceso a todos mis 4 núcleos. Lo comprobé con la ejecución simultánea de varios ejecutables y System Monitor. Pero cuando intento ejecutar este código, está usando solo un núcleo y no está obteniendo ningún beneficio del procesamiento paralelo.

¿Qué estoy haciendo mal?

Respuesta

24

Probablemente necesidad de revisar la Concurrency section of the Go FAQ, específicamente estas dos preguntas, y averiguar qué (si no ambos) se aplican a su caso:

¿Por qué mi programa de multi-goroutine uso CPUs múltiples

debe establecer el entorno de shell GOMAXPROCS variable o utilizar el similar-nombrado function del paquete de tiempo de ejecución para permitir que el tiempo de ejecución apoyo para utilizar más de una hebra de OS.

Los programas que realizan el cómputo paralelo se deben beneficiar de un aumento en GOMAXPROCS. Sin embargo, tenga en cuenta que concurrency is not parallelism.

¿Por qué usar GOMAXPROCS> 1 a veces hace que mi programa sea más lento?

Depende de la naturaleza de su programa . Los programas que contienen varios goroutines que pasan mucho tiempo en los canales de comunicación se experiencia degradación del rendimiento cuando se utilizan múltiples hebras de SO. Este se debe a la importante penalización de cambio de contexto implicada en al enviar datos entre subprocesos.

no goroutine planificador de Go es tan bueno como que tiene que ser. En el futuro, se debe reconocer los casos y optimizar su uso de hebras de SO. Para ahora, GOMAXPROCS se debe establecer en por aplicación.

Para obtener más detalles sobre este tema, consulte la conversación titulada Concurrency is not Parallelism.

+1

también tenga en cuenta que el valor predeterminado parece ser "1" – mnagel

+1

El valor predeterminado con go1.6.3 en OSX 10.11 es la cantidad de núcleos de CPU. Creo que fue cambiado en Go v1.5. – Xeoncross

Cuestiones relacionadas