Ver Mensaje Individual
  #3 (permalink)  
Antiguo 05/08/2014, 10:39
SARGE553413
 
Fecha de Ingreso: febrero-2014
Mensajes: 55
Antigüedad: 10 años, 2 meses
Puntos: 3
Respuesta: Variable synchronized en C# o en c++/cli

Hola de nuevo, he estado "investigando" y he encontrado una manera, un tanto farragosa, de conseguir variables al estilo de synchronized de Java. Lo he probado en C++/CLI, pero estoy casi seguro de que en C# se puede hacer igual, solo que de este último no tengo conocimientos.

Lo hago mediante propertys, simplemente declaro un objeto extra en mi clase (de tipo Object por ej., llamado 'lock'), y luego declaro la variable que quiero "synchronized" como si fuera property, y defino sus métodos get y set haciendo Monitor::Enter/Exit(lock); (obviamente usando una variable auxiliar para no caer en recursividad infinita). Se ve perfectamente con un ejemplo:

Código:
//fichero de cabecera (.h)

ref class prPrty
{
public:
	prPrty();

	Thread^ thMethod();
	void thAux();
	int getA();

private:

	property int a{
		int get(){
			Monitor::Enter(lock);
			Thread::Sleep(3000);
			return __a;
			Monitor::Exit(lock);
		}

		void set(int _a){
			Console::WriteLine("sin lock");
			Monitor::Enter(lock);
			Console::WriteLine("con lock");
			Thread::Sleep(3000);
			__a = _a;
			Monitor::Exit(lock);
		}
	}

	int __a;

	Object ^lock;
};

/*********************************/

//Fichero fuente (.cpp)

#include "prPrty.h"


prPrty::prPrty(){
	this->lock = gcnew Object();
}

Thread^ prPrty::thMethod(){
	Thread ^th = gcnew Thread(gcnew ThreadStart(this, &prPrty::thAux));
	th->Start();
	return th;
}

void prPrty::thAux(){
	this->a = 20;
}

int prPrty::getA(){
	int aux;
	Console::WriteLine("\tEsperando para el lock...");
	Monitor::Enter(lock);
	Console::WriteLine("\tlock obtenido");
	aux = a;
	Monitor::Exit(lock);
	return aux;
}

/*********************************/

//main (.cpp)

int main(){
	prPrty ^a = gcnew prPrty();
	Thread ^th=a->thMethod();
	Thread::Sleep(500);
	Console::WriteLine("\t\t"+a->getA());
	th->Join();
	Console::ReadLine();
	return 0;
}
Si esto que he probado no demuestra nada, o es incorrecto, por favor explicadlo si podéis.

Gracias, saludos.