Autor
|
Tema: Pequeña ayudita porfavor (threads/hilos) :) (Leído 4,040 veces)
|
Thorn14
Desconectado
Mensajes: 4
|
Hola, buenas a todos! Tengo un problemilla con este programa. Tengo que hacer que de como resultado el numero pi pero no se que hago mal que las interaciones no me funcionan correctamente (algunos numeros se repiten) y hace que el proceso falle. Esta hecho con threads. Cualquier ayuda sera bienvenida! # include <stdio.h> # include <stdlib.h> # include <string.h> # include <unistd.h> # include <pthread.h> double factores [1000]; int i,N; double step,x, totalsum, pi; void *calcularsum (void *argument){ x = (i+0.5)*step; factores[i] = 4.0/(1.0+x*x); } int main (int argc, char *argv[]) { if (argc != 2){ printf("Se ha de introducir un valor. Ejemplo: ./pi 10\n"); }else{ step = 1.0/N; pthread_t h[N]; for (i=0; i<N; i++) { pthread_create(&h[i] , NULL , calcularsum , NULL); } for (i=0; i<N; i++){ pthread_join(h[i], NULL); totalsum = factores[i] + totalsum; } pi = totalsum * step; } return 0; }
Al hacer el "printf("%f\n",totalsum); " para comprobar que numeros van haciendo los diferentes threads, me encuentro con que alguna vez (random) la hace bien, pero lo mas normal es que el primer número salga como 0.000000 y/o algunos otros se repitan. El resultado de ejecucion seria: ./pi 10 0.000000 3.911980 7.676686 7.676686 11.003090 14.074107 16.886058 19.446058 21.768264 23.870761 2.3870760525 En cambio otra vez, es un número mas aproximado a pi: ./pi 10 3.990025 7.902005 11.666711 15.230186 18.556589 21.627606 24.439557 26.999557 29.321763 31.424260 3.1424259850
|
|
« Última modificación: 9 Enero 2014, 21:35 pm por Thorn14 »
|
En línea
|
|
|
|
ivancea96
Desconectado
Mensajes: 3.412
ASMático
|
Pon etiquetas de código GeSHi de C o C++ y comentarios en el código para mayor comprensión.
|
|
|
En línea
|
|
|
|
Thorn14
Desconectado
Mensajes: 4
|
La cosa es que no se si los pthread_create y pthread_join estan hechos correctamente, no domino mucho de hilos
|
|
|
En línea
|
|
|
|
ivancea96
Desconectado
Mensajes: 3.412
ASMático
|
Aunque nunca usé esos threads, te puedo dar esto: Info. Y decirte, que pruebes en un ejemplo a parte más sencillo.
|
|
|
En línea
|
|
|
|
amchacon
Desconectado
Mensajes: 1.211
|
El problema que veo ahí es: x = (i+0.5)*step; factores[i] = 4.0/(1.0+x*x);
Mientras un hilo está modificando la variable x, mientras otros hilos lo están usando. Si tienes suerte y se sincronizan bien pues te sale, pero como modifiques esa variable x mientras lo está usando el otro hilo... O te sale mal el resultado o en algún caso extremo tu progama podría hacer un abort. Puedes ponerte un mutex para un acceso sincronizado pero, creo que sería más eficiente evitar variables globales que puedan dar colisión. He aquí mi propuesta: #include <stdio.h> #include <pthread.h> double factores [1000],step; void *calcularsum (void *argument) { int i = *((int*) argument); double x = (i+0.5)*step; factores[i] = 4.0/(1.0+x*x); free(argument); } int main (int argc, char *argv[]) { int* P; int N,i; double totalsum,pi; if (argc != 2) { printf("Se ha de introducir un valor. Ejemplo: ./pi 10\n"); } else { N=atoi(argv[1]); step = 1.0/N; pthread_t h[N]; for (i=0; i<N; i++) { P = (int*)malloc(sizeof(int)); *P = i; pthread_create(&h[i] , NULL , calcularsum ,P); } for (i=0; i<N; i++) { pthread_join(h[i], NULL); totalsum = factores[i] + totalsum; printf("%f\n",totalsum); } pi = totalsum * step; printf("%.10f\n", pi); } return 0; }
No tengo linux a mano ahora, pero debería funcionar.
|
|
« Última modificación: 9 Enero 2014, 22:26 pm por amchacon »
|
En línea
|
|
|
|
Thorn14
Desconectado
Mensajes: 4
|
Si, modificando lo que has comentado, no pasa lo que comentaba. Muchas gracias, ya había pensado también en que podría ser un problema de variables. Si no es mucha molestia, me podrías explicar que hace las siguientes lineas que has comentado: int i = *((int*) argument); P = (int*)malloc(sizeof(int)); *P = i;
|
|
|
En línea
|
|
|
|
amchacon
Desconectado
Mensajes: 1.211
|
int i = *((int*) argument); argument es un puntero void, si quiero guardarlo en un entero primero tengo que hacerle un cast a puntero int* y después obtener el valor del entero con un *. Para profundizar más, mirate explicaciones de punteros en C. Por cierto, son muy importantes. P = (int*)malloc(sizeof(int)); malloc reserva memoria de forma dinamica, he aquí una explicación de memoria dinámica: http://foro.elhacker.net/programacion_cc/duda_memoria_dinamica_en_c-t391783.0.htmlAhí uso el new de C++, pero es lo mismo. Después de reservar la memoria guardo un puntero en P, previamente hay que hacer un cast a (int*) ya que P es un puntero a entero. *P = i; P es un puntero, para cambiarle el valor a su contenido tengo que usar el operador *
|
|
|
En línea
|
|
|
|
Thorn14
Desconectado
Mensajes: 4
|
Todo listo, muchas gracias por su tiempo y sus explicaciones.
|
|
|
En línea
|
|
|
|
|
Mensajes similares |
|
Asunto |
Iniciado por |
Respuestas |
Vistas |
Último mensaje |
|
|
Una pequeña ayudita :)
Ejercicios
|
yrrtni
|
0
|
3,093
|
25 Octubre 2008, 14:52 pm
por yrrtni
|
|
|
Hilos Threads
Java
|
pastafariana
|
0
|
1,618
|
12 Marzo 2013, 20:12 pm
por pastafariana
|
|
|
Duda sobre threads (hilos) y semáforos (mutex)
Programación C/C++
|
IngenieroFrustrado
|
3
|
2,973
|
25 Enero 2014, 11:17 am
por amchacon
|
|
|
Duda con threads o hilos
Java
|
.:UND3R:.
|
1
|
2,402
|
14 Febrero 2014, 17:59 pm
por Gh057
|
|
|
Threads, Hilos en C++
Programación C/C++
|
Ahustinkrone
|
5
|
10,834
|
17 Junio 2014, 16:10 pm
por daryo
|
|