Duda con threads

Iniciado por patilanz, 15 Mayo 2014, 13:33 PM

0 Miembros y 1 Visitante están viendo este tema.

patilanz

Hola me acabo de enterar de que existe thread http://www.cplusplus.com/reference/thread/thread/

Esto me gusto porque deberia de funcionar en todos los os.
Luego probe hacer esto:

Código (cpp) [Seleccionar]
#include <thread>
#include <stdio.h>
#include <thread>
#include <iostream>

using namespace std;
void hilo(int n){
int i=0;
while(i<100){
i++;
cout << "Thread " << n << " :" << i << endl;
}
}

int main(int argc, char ** argv){
thread test(hilo,1);
test.join();
thread test2(hilo,2);
test2.join();
getchar();
}


Y el resultado fue como si hubiera puesto dos whiles seguidos. No deberia de mostrar se por ejemplo:

Thread 1: 1
Thread 2: 1
Thread 1: 2
...
En vez de:

Thread 1: 1
Thread 1: 2
...
Thread 1: 100
Thread 2: 1
..


O tengo confundido lo que hacen los threads?

Saludos

NikNitro!

los threads se ejecutan de forma aleatoria. No tienen por qué ocurrir siempre igual.

De todos modos no estoy seguro de que en c++ se usen así.

En Java (que es donde los estoy dando actualmente) tienes que hacer que la clase extienda de threadable y llamar a un método que es run() el cual es override.

Saludos

patilanz

En mi caso no se ejecutan de forma aleatoria porque va todo seguido como en dos whiles seguidos.

amchacon

#3
No hay ningún problema ahí, nadie te garantiza que un thread van a ir al mismo tiempo (depende de los núcleos físicos que tengas, la carga del sistema...).

Si quieres un orden fijo, tendrás que sincronizar los threads con los mecanismos correspondientes.




Vale lo acabo de revisar y efectivamente has metido la gamba xD.

El problema está aquí:
Código (cpp) [Seleccionar]
thread test(hilo,1);
test.join();
thread test2(hilo,2);
test2.join();


Ponlo así:
Código (cpp) [Seleccionar]
thread test(hilo,1);
thread test2(hilo,2);
test.join();
test2.join();


El join no es para iniciar el thread, sino para esperar a que acabe xD
Por favor, no me manden MP con dudas. Usen el foro, gracias.

¡Visita mi programa estrella!

Rar File Missing: Esteganografía en un Rar

patilanz

Gracias ahora funciona perfecto  ;D
Pero si es para esperar a que acabe que hace? Cuando acaba la función limpia memoria o algo así?
Puedo detectar que el thread se ha cerrado y ejecutar otra función con join?

amchacon

La idea es la perfecta sincronización, si vas a salir del programa tendrás que esperar a que terminen el resto de los hilos. De lo contrario podría tener efectos adversos.

La clase thread presupone que harás join en algún momento (al final del programa/funcion normalmente), si tu idea es dejar el hilo a tu aire tienes que usar detach():
Código (cpp) [Seleccionar]
thread t(hilo);
t.detach();


Pero pocos son los casos que es necesario tirar por ahí.

CitarPuedo detectar que el thread se ha cerrado
¿Sin usar join?

No, a no ser que te pongas un booleano de control en el hilo... Lo más natural sería el uso de condiction_variables.

Citary ejecutar otra función con join?
No, una vez que haz hecho join no puedes ejecutar otra funcion.

Aunque si puedes aprovecharte del move-constructor y crear otro objeto thread:
Código (cpp) [Seleccionar]
thread t(hilo);
t.join();

t = thread(hilo2); // move contructor
Por favor, no me manden MP con dudas. Usen el foro, gracias.

¡Visita mi programa estrella!

Rar File Missing: Esteganografía en un Rar

patilanz

Hola gracias por tu explicacion pero ahora tambien con los threads pero anadiendo socket de windows este codigo funciona fuera de un thread pero si lo pongo dentro de una funcion que llamo desde el thread pasando le los parametros me da error abort was called.

Código (cpp) [Seleccionar]
void newClient(SOCKET &socket_s,SOCKET &socket_c,sockaddr_in &client){
cout << "Socket from: " << inet_ntoa(client.sin_addr) << endl;
char buffer[512];
int result=recv(socket_c,buffer,sizeof(buffer),0);
if(result==-1)
return (void)WSAGetLastError();
cout << buffer;
}
thread(newClient,socket_s,socket_c,client);


Si pongo el codigo directamente en la funcion main donde se hace el acept funciona pero en cambio en la funcion con el thread no.

Si llamo la funcion aparte si funciona... ??
Porque??

Saludos y gracias

ivancea96

Asegúrate de hacerle .join() o .detach() al thread.

amchacon

Hay varios errores ahí.

El primero esque no asignas ningun identificador para el objeto thread:
Código (cpp) [Seleccionar]
thread unHilo(newClient,socket_s,socket_c,client);

Mejor asi, no te olvides después hacer un join() antes de terminar.

Por cierto, los argumentos con referencia deben de indicarse con ref. De modo que debería ser así:
Código (cpp) [Seleccionar]
thread unHilo(newClient,ref(socket_s),ref(socket_c),ref(client));

Por favor, no me manden MP con dudas. Usen el foro, gracias.

¡Visita mi programa estrella!

Rar File Missing: Esteganografía en un Rar

patilanz

Gracias ahora funciona. La documentacion thread es algo mala en ningun lugar pone lo de ref()

Y una ultima pregunta  ;D
Puedo hacer join del thread desde la función que llama el thread?
Lo necesito porque tengo un thread que hace los listen pero tiene que ser multiusuario por lo tanto el thread no puede tener nombre ni me puedo parar a esperar para que el thread se cierre si no que se tiene que terminar solo con join cuando el usuario se valla, esto ya lo detecto con los sockets.