PRIMITIVAS DE SINCRONIZACIÓN BASADAS EN MEMORIA COMPARTIDA.
|
|
- Sofia Arroyo Sosa
- hace 6 años
- Vistas:
Transcripción
1 PRIMITIVAS DE SINCRONIZACIÓN BASADAS EN MEMORIA COMPARTIDA. En este modulo vamos a presentar una serie de técnicas que permitan resolver los problemas inherentes a la programación concurrente, apoyándose en la existencia de una memoria común accesible a todos los procesos involucrados. Primero se verá el mecanismo de semáforos, (se analizará como se pueden definir y utilizar los semáforos por medio de las operaciones definidas para interaccionar con ellos). Luego se describirá como se puede resolver problemas concurrentes (utilizando semáforos por medio de problemas clásicos de la programación concurrente: esquema productor consumidor, el problema de los lectores y escritores, y el problema de la comida de los filósofos), y la implementación de los semáforos. Por último se tratarán aspectos relacionados con la sincronización de hilos en java. Segundo: se analizará el mecanismo de las Regiones Críticas Condicionales (RCC). Si bien no fueron muy utilizadas en los lenguajes diseñados para la programación concurrente, desde el punto de vista didáctico es válido analizarlo, porque constituyen un escalafón intermedio entre un mecanismo de bajo nivel como son los semáforos y uno de alto nivel como los monitores. Tercero: monitores. El primer avance en la resolución de problemas de procesos concurrentes llego en 1965, con el artículo publicado por Dijkstra. Quien estaba interesado en el diseño de un sistema operativo como un conjunto de procesos secuenciales cooperantes y en el desarrollo de mecanismos eficientes y fiables para dar soporte a la cooperación. Los procesos de usuarios podrían utilizar estos mecanismos si el procesador y el sistema operativo lo hacían posible. El principio fundamental postulado fue: si dos o mas procesos pueden cooperar por medio de simples señales, de forma que se pueda obligar a detener a un proceso en una posición determinada hasta que reciba una señal específica. Cualquier requisito complicado de coordinación puede satisfacer por medio de la estructura de señales adecuada. Para la señalización, se usan variables especiales llamadas semáforos. Para transmitir una señal por el semáforo s, los procesos ejecutan las operaciones signal(s), Para recibir una señal del semáforo s, los procesos ejecutan la operación wait(s); si la señal aún no se ha transmitido, el proceso es suspendido hasta que tenga lugar la transmisión. Nota: En el artículo de Dijkstra se emplea la letra P para wait y V para signal, que son las iniciales de las palabras holandesas que significan comprobar (proberen) e incrementar (verhogen). Las soluciones a la exclusión mutua tienen desventajas que los procesos esperan de una forma activa. Un proceso que no está haciendo nada ocupa un procesador limitando la eficiencia del sistema. A continuación vamos a ver la primitiva de comunicación entre procesos SEMAFOROS que bloquea al proceso en vez de desperdiciar tiempo de cpu cuando no se le permite entrar a su sección crítica o realizar una acción determinada. Es un mecanismo de más bajo nivel que otros por su potencia. Un semáforo se puede definir como una variable tipo semaphore, y puede ser utilizado en la definición de arrays y registros. var sem: semaphore; sem_array: array [1..10] of semaphore; type sen_record=record of s:semaphore; i:integer; -1
2 Podemos considerar que un semáforo es un tipo de dato abstracto que admite valores enteros no negativos, si solo toma valores 0 y 1 es binario, en cualquier otro caso es uno general. Las operaciones que se pueden realizar con un semáforo son: 1. wait(s): Decrementa el valor de s si es mayor a 0 y si s es =0 el proceso se bloqueará en el semáforo. 2. signal(s). desbloquea algún proceso bloqueado en s, encaso que haya ningún proceso incrementa el valor de s. 3. initial(s,v). se utiliza para inicializar el semáforo s al valor v donde, esta operación es exclusiva de pascal-fc y solo puede ser usada en el programa principal. Teniendo en cuenta las anteriores definiciones, wait y signal se pueden expresar como: wait(s): if s>0 then s:=s-1 else bloquear proceso; signal(s): if (hay procesos bloqueados) then desbloquear un proceso else s:=s+1; Las operaciones wait y signal implican una comparación y actualización de la variable entera asociada o, en su caso, el bloqueo y desbloqueo de los procesos. Una de las principales características de los semáforos es que todas las operaciones asociadas a wait y signal deben ejecutarse en forma indivisible, es decir, la utilización de un semáforo implica las exclusiones mutuas en la ejecución de las operaciones sobre él definidas. Los semáforos hacen uso de las funciones proporcionadas por el sistema operativo para bloquear a los procesos, provocando una espera con bloqueo. Puede suceder que se ejecute una operación signal sobre un semáforo en el existan varios procesos bloqueados, solo un proceso se debería desbloquear. Si bien se podría utilizar cualquier política de gestión para la cola de procesos bloqueados, la única política válida es la política FIFO, puesto que de lo contrario podrían quedar procesos que nunca se desbloqueen. RESOLUCIÓN DE PROBLEMAS USANDO SEMÁFOROS: Los semáforos son una herramienta general para resolver problemas de sincronización. Veremos cómo se resuelve el problema de exclusión mutua y la condición de sincronización y una serie de problemas clásicos de la programación concurrente. Exclusión mutua y condición de sincronización. Para implementar una solución a la exclusión mutua, cada sección crítica debe ir precedida por la operación wait sobre un semáforo binario y debe terminar con una operación signal sobre ese semáforo. Todas las secciones críticas mutuamente exclusivas deben usar el mismo semáforo que se inicializa a 1. La solución a la exclusión mutua usando semáforos se plantea de la forma que se muestra a continuación: process p1;.. wait(s); sección crítica 1; signal(s);.. Process Pk;.. wait(s); sección crítica k; signal(s); -2
3 Para implementar la condición de sincronización se asocia un semáforo general a cada condición (ejemplo asignación de recursos). Cuando un proceso ha hecho que se cumpla una determinada condición c, lo indica ejecutando un signal sobre el semáforo de la condición. Un proceso espera a que la condición sea verdad ejecutado una condición wait sobre un semáforo asociado a dicha condición. El valor de los semáforos indica el número de recursos disponibles en cada momento. Veremos la resolución con semáforos de algunas sincronizaciones que planteamos: Ejemplo 1: dado dos procesos concurrentes p1 y p2, donde p2 no puede ejecutar d hasta que p1 ejecute a process p1; a; b; Process P2; c; d; Resolveremos el problema usando un semáforo s con valor inicial 0 sobre el que p1 y p2 realizarán las siguientes operaciones: process p1; Process P2; a; c; signal(s); wait(s); b; d; Si queremos que los dos procesos anteriores se esperen en un punto medio, usaremos los semáforos s y t, inicializados a 0 de la siguiente forma: process p1; Process P2; a; c; signal(s); signal(t); wait(t); wait(s); b; d; Es fácil caer en interbloqueos, usando los semáforos, ejemplo: al cambiar el orden de las operaciones anteriores. Ejemplo 2: supongamos 3 procesos concurrentes process p1; a; b; Process P2; c; d; end Process P3; e; f; y queremos que p2 solo pueda ejecutar d si p3 ha ejecutado e, o p1 ha ejecutado a. para implementar esta sincronización usaremos el semáforo s con valor inicial 0: process p1; a; signal(s); b; Process P2; c; wait(s); d; Process P3; e; signal(s); f; -3
4 si en el enunciado anterior la condición lógia es una y, es decir p1 ha ejecutado a y p3 ha ejecutado e, podríamos implementar la sincronización usando el mismo semáforo s con valor inicial 0 y añadiendo una operación wait(s) en el proceso p2: process p1; a; signal(s) b;; Process p2; c; wait(s); wait(s); d; Process p3; e; signal(s) f; Sin embargo, si p1 se ejecutara 2 veces muy rápido, p2 podría ejecutar d sin que p3 ejecutara e. la solución correcta debe usar 2 semáforos s y t con valor inicial 0: process p1; a; signal(s) b;; Process p2; c; wait(s); wait(t); d; Process p3; e; signal(t) f; PROBLEMAS CLÁSICOS: Vamos a ver una serie de problemas de sincronización, importantes principalmente debido a que son ejemplos de una amplia clase de problemas de control de concurrencia: CASO 1: EL PROBLEMA DEL PRODUCTOR CONSUMIDOR Los productores /consumidores son corrientes en los sistemas operativos. Un proceso productor genera información que es utilizada por un proceso consumidor, el siguiente esquema muestra el trabajo de un proceso productor y un consumidor a través de un buffer compartido: un proceso productor deposita información en el buffer que es extraída por un proceso consumidor Productor Consumidor Por ejemplo, para imprimir un trabajo, el ordenador (productor) deposita información en un buffer y la impresora (consumidor). Por la diferencia de velocidad entre ordenador e impresora es necesario un mecanismo de sincronización. Para que se ejecuten concurrentemente los procesos productores y consumidores tenemos que crear un buffer que sea alimentado por el productor y vaciado por el consumidor. De modo que el consumidor no trate de consumir elementos aun no producido, si es así deberá esperar a que suceda un elemento. Otro aspecto es el acceso en exclusión mutua al buffer. Si tenemos un productor y un consumidor no sería necesario que el acceso al buffer se realice en exclusión mutua, pero con varios productores y/o consumidores si, puesto que dos productores podrían tratar de colocar elementos en la misma posición de buffer. El problema del productor/consumidor con buffer ilimitado no establece límite al tamaño del buffer, el productor siempre podrá producir y almacenar elementos. El problema del productor/consumidor con buffer limitado, tenemos un número fijo de posiciones en el buffer n. el productor deberá esperar si todas las posiciones están llenas y el consumidor si todas están vacías. El esquema general para este problema sería: -4
5 process productor; producir un elemento; protocolo de entrada; insertar elemento en el buffer; protocolo de salida; ; process consumidor; protocol de entrada; extraer elemento del buffer; protocolo de salida; consumir elemento; ; Para resolver este problema se usaran los siguientes semáforos: Mutex: permitirá controlar el acceso en exclusión mutua al buffer y se inicializará 1. Vacios: nos permitirá contar el número de posiciones vacías del buffer y se inicializará n. cuando no quedan posiciones vacía en buffer, tendrá valor 0, con lo que cualquier productor que intente acceder al buffer será bloqueado, lo consumidores son los que incrementarán el valor de este semáforo (mediante signal), cada vez que libere una posición del semáforo. Llenos: cuenta el número de posiciones llenas del buffer, se inicializará a 0. Permite bloquear a los consumidores cuando no existan elementos. Teniendo en cuenta los anteriores semáforos una posible solución sería: process productor; producir item; wait(vacios); wait(mutex); buffer [frente]:=item; frente :=(frente +1) mod N; signal(mutex); signal(llenos); ; process consumidor; wait(llenos); wait(mutex); item:= buffer [cola]; cola:=(cola+1) mod N; signal(mutex); signal(vacios); consumir ítem; ; Una vez que el productor ha producido un elemento, ejecuta la operación wait(vacios). Si existen elementos en el buffer (vacios>0), la ejecución del wait decrementará el valor de semáforo, indicando que hay una posición libre menos en el buffer. Si buffer está lleno (vacío=0), el productor se quedará bloqueado esperando que se libere un hueco. Son los consumidores los únicos que pueden ejecutar un signal(vacío) para indicar que ya existe una posición libre mas en el buffer. CASO 2: EL PROBLEMA DE LOS LECTORES Y ESCRITORES Si tenemos un recurso representado por un objeto de datos que se debe compartir entre varios procesos concurrentes (un fichero o BD). Algunos pueden querer leer el contenido del objeto compartido (lectores), mientras que otros actualizarlos (escritores). Si dos o más lectores acceden al objeto de datos compartido simultáneamente no habría inconvenientes, pero si, el en caso que un escritor y algún otro proceso (lector o escritor) acceden simultáneamente. Para evitar esto necesitamos que los escritores tengan acceso exclusivo al objeto compartido. Este problema de sincronización se conoce como de lectores escritores. El esquema para cada uno de los posibles procesos sería: co lector*1+;;lector*n+;escritor*1+;;escritor*n+; coend process type lector; -5
6 protocolo de entrada; Leer del recurso; protocolo de salida; process type escritor; protocolo de entrada; Escribir en el recurso; protocolo de salida; El problema de los lectores y escritores tiene distintas versiones, dependiendo de a qué tipo de procesos demos prioridad para acceder al recurso: 1. prioridad en la lectura: ningún lector debe esperar salvo que un escritor haya obtenido permiso para usar el objeto compartido. (Ningún lector espera a que otros lectores acaben por el hecho que un escritor este esperando). 2. Prioridad en escritura: una vez que un escritor está esperando, debe realizar su escritura tan pronto como sea posible. (si un escritor espera, ningún lector nuevo debe inicializar su lectura). Para los casos planteados podemos observar que pueden ocasionar falta de equidad. En el primer caso pueden verse afectados los lectores y en el segundo los escritores. Para resolver el problema con prioridad en la lectura, vamos a usar las siguientes variables: 1. Una variable entera n1 inicializada a 0, que indica el número de lectores que hay en el recurso compartido en un momento dado. 2. Un semáforo mutex inicializado a 1 para asegurar la exclusión mutua cuando se actualiza n1. 3. Un semáforo wrt inicializado a 1 común a lectores y escritores. Funciona como semáforo de exclusión mutua para los escritores. También lo utiliza el primer/ultimo lector para entrar/salir de la sección crítica. Pero no lo usan los lectores que entran y salen mientras otro lector ya se encuentra en la sección crítica.una posible solución sería: process type lector; wait(mutex); n1:=n1+1; (* se impide que entre un escritor*); if(n1=1) then wait (wrt); signal(mutex); leer del recurso;. wait(mutex); n1:=n1-1; (* el ultimo lector trata de desbloquear a algún escritor*) if (n1=0) then signal (wrt); signal(mutex); process type escritor; (* la escritura se hace en exclusion mutual*) wait(wrt); escribir en el recurso; signal (wrt); La clave de esta solución radica en la operación wait(wrt) que realiza el primer lector que accede al recurso, pues el semáforo wrt alcanzara valor 0, impidiendo que los escritores accedan al recurso. En este -6
7 caso no hay exclusión mutua entre los proceso, sino que los lectores pueden entrar al recurso a la vez. No se garantiza la equidad, si llegan lectores continuamente no dejaran pasar a los escritores. La solución con prioridad en escritura se pude plantear como: Una variable entera n1, que cuenta el número de lectores en el recurso (inicializada a 0).. Una variable entera nee, para contar el número de escritores esperando para entrar al recurso. (Inicializada a 0). Una variable booleana escribiendo que indica si hay un escritor en el recurso accediendo al recurso (inicializada en false). El acceso a estas variables se hará en exclusión mutua con un semáforo binario mutex (con valor inicial 1). Con este planteamiento la solución sería: process type lector;. wait(mutex); (*mientras existan escritores en espera o algún escritor este escribiendo esperar.*) while (escribiendo or nee>0) do signal (mutex); wait(mutex); n1:=n1+1; signal(mutex); leer del recurso; wait(mutex); n1:=n1-1; signal(mutex); process type escritor;. wait(mutex); (* mientras algún escritor este accediendo al recurso o existan lectores leyendo hay que esperar.*) nee:=nee+1; while (escribiendo or n1>0) do signal (mutex); wait(mutex) escribiendo:=true; nee:=nee-1; signal(mutex); Escribir en el recurso; wait(mutex); escribiendo:=false; signal(mutex); Se puede demostrar que se cumple las condiciones establecidas en la descripción del problema: Si un escritor está escribiendo, cuando hizo la comprobación del while escribiendo=false y n1=0, y antes de entrar en el recurso pone escribiendo=true, entonces ningún escritor o lector satisfará la -7
8 condición del while del protocolo de entrada y esperará a la espera de entrar en el recurso hasta que el escritor salga del recurso y escribiendo =false en su protocolo de salida. Si un lector está leyendo, n1>0, entonces los escritores deben esperar en el protocolo de entrada. Si un escritor llega, realiza la operación nee=nee+1, todos los lectores que no estaban en el recurso y deseen entrar deben esperar en el protocolo de entrada, los escritores tienen preferencia sobre los lectores Sin embargo las sentencias while producen espera ocupada. Para evitar la espera ocupada se plantea el uso de las siguientes variables: Semáforo mutex inicializado a 1 para proporcionar exclusión mutua en uso de variables compartidas Los semáforos lector y escritor inicializados a 0, el semáforo lector bloqueará a un lector cuando este no deba entrar al recurso. Las variables enteras n1,nl, nee inicializadas a 0 que indican el número de lectores en el recurso, el numero de procesos lectores esperando entrar en el recurso y el numero de escritores esperando, y una variable booleana escribiendo que indica si un escritor está accediendo al recurso. process type lector;. wait(mutex); (*mientras está escribiendo o existan escritores en espera el lector debe ser bloqueado.*) If (escribiendo or nee>0) then nle:=nle+1; signal (mutex); wait(lector); nle:=nle-1; n1:=n1+1; if (nle>0) then (* desbloqueo encadenado*) signal(lector); else signal(mutex); Leer del recurso;. wait(mutex); n1:=n1-1; (*desbloquear un escritor si es possible *) If (n1=0 and nee>0) then signal(escritor); else signal(mutex) process type escritor;. wait(mutex); (* Si se está escribiendo o existen lectores el escritor debe ser bloqueado.*) If (escribiendo or n1>0) then nee:=nee+1; signal (mutex); wait(escritor) nee:=nee-1; escribiendo:=true; signal(mutex); -8
9 Escribir en el recurso; wait(mutex); ne:=ne-1; (* Desbloquear un escritor que este en espera sino desbloquear a un lector en espera*) If (nee>0) then signal(escritor) else if(nle>0) then signal(lector) else signal(mutex) En esta solución hay que tener en cuenta: 1) debido a que se permite la concurrencia de lectores en el momento en que el lector acceda al recurso, el resto de los lectores también deberían acceder, por desbloqueo encadenado situado en el protocolo de entrada de los lectores: if(nle>0) then signal(lector) else signal(mutex) Antes que el lector accede al recurso comprueba si otros lectores están en espera, si es afirmativo desbloquea uno de ellos (signal (lector)) y accede al recurso, el lector desbloqueado realiza la misma comprobación y desbloquea al siguiente lector, esto se repite hasta desbloquear al último lector en espera, siendo este el que libera la exclusión mutua antes de acceder al recurso. 2) la cesión de la exclusión mutua: se produce cuando un proceso que ha adquirido con anterioridad la exclusión mutua realiza un signal sobre un semáforo sin liberal la exclusión mutua, de esta forma el proceso que es desbloqueado por el signal (si existe), comienza su ejecución en posesión de exclusión mutua (ver de ejemplo anterior protocolos de salidas y desbloqueo encadenado). Para solucionar el problema de inanición que se puede producir con los lectores, se puede cambiar el protocolo de salida del escritor para dar prioridad a los lectores en espera. Para conseguir esto, es necesario cambiar el orden de las comprobaciones, cotejando si es posible desbloquear a algún lector. CASO 3: EL PROBLEMA DE LA COMIDA DE LOS FILÓSOFOS Este problema propuesto por Dijkstra, es un problema clásico no por su importancia práctica, sino porque sirve para ilustrar los problemas básicos del interbloqueo ya que las condiciones para que se pueda producir un interbloqueo están presentes en su enunciado. Puede verse como un caso representativo de los problemas relacionados con la coordinación de los recursos no compartible de un sistema. El problema se puede enunciar de la siguiente manera: Cinco filósofos dedican sus vidas a pensar y comer (estas dos acciones son finitas en el tiempo). Los filósofos comparten una mesa rodeada de cinco sillas, cada una de un filósofo. En el centro de la mesa ha comida, y en la mesa cinco palillos y cinco platos. Ver figura Cuando un filósofo no se relaciona con sus colegas se supone que está pensando (o realizando una actividad mas productiva para la sociedad). De vez en cuando, un filósofo -9
10 siente hambre y se dirige a su silla y trata de tomar los dos palillos que están más cerca de él. Cuando un filósofo tiene sus dos palillos simultáneamente, come sin dejar sus palillos. Cuando ha acabado de comer, vuelve a dejar los dos palillos y empieza a pensar de nuevo. La solución al problema, por lo tanto consiste en inventar algoritmo que permita comer a los filósofos, Una solución sencilla consiste en representar cada palillo por un semáforo. Un filósofo trata de tomar el palillo ejecutando una operación wait sobre el semáforo. Var palillo: array[0..4] of semaphore Donde los cinco semáforos están inicializados a 1. La estructura de un proceso filósofo será: porcess type filosofo (i:integer); piensa; wait(palillo[i]); wait(palillo[(i+1)] mod 5); come; signal(palillo[i]); signal(palillo[(i+1) mod 5]); Cada filósofo toma primero el palillo de su izquierda y después, el de la derecha. Cuando un filósofo termina de comer, devuelve los dos palillos a la mesa. Esta solución garantiza que no hay dos vecinos comiendo simultáneamente; sin embargo, es rechazada porque hay peligro de interbloqueo. Supongamos que los cinco filósofos están hambrientos a la vez, y que cada una toma el palillo de su izquierda y todos tratan de tomar el otro palillo que no estará disponible. Para solucionar este problema de interbloqueo veremos distintas propuestas: - Permitir que como máximo cuatro filósofos se sienten simultáneamente a la mesa. Esto permite que muchos filósofos tomen un palillo y se ralentice en proceso, pero al menos alguno de los filósofos tendrá acceso a los dos palillos. Para ello, usamos el semáforo sitio inicializado a 4 de la siguiente forma: process tye filosofo(i: integer); piensa; wait(sitio); wait (palillo[i]); wait(palillo[(i+1) mod 5]); come; signal(palillo[i]); signal(palillo[(i+1) mod 5]); signal(sitio); - Permitir que un filósofo tome sus palillos solamente si ambos están libres. En este planteamiento usaremos las siguientes variables: Un array de booleanos libres de tamaño 5, de esta forma que cada elemento del array tome valor true si el palillo correspondiente está libre o false si está ocupado. Inicialmente todos los elementos estarán inicializados a true (es decir, libres) y no ejecutaría las instrucciones wait si esto no es así. Un semáforo mutex inicializado a 1 para acceder en exclusión mutua al array libres. La solución es la siguiente: process tpe filosofo(i:integer); piensa; -10
11 wait(mutex); while ot (libres[i] and libres[(i+1) mod 5] do signal (mutex); wait(mutex) libres[i]:=false; libres[(i+1) mod 5]:= false; signal(mutex); come; wait(mutex); libres[i]:=true; libres[(i+1) mod 5]:=true; signal(mutex); Sin embargo esta solución se basa en la espera ocupada, y por lo tanto, no es del todo eficiente. - Usando una solución asimétrica, es decir, un filósofo impar toma primero su palillo de la izquierda y luego el palillo de la derecha, mientras que un filosofo par elije su palillo de la derecha y luego el de la izquierda. Para implementar esta solución usaremos el array palillo de cinco semáforos inicializados a 1. process type filosofo_par(i:integer); piensa; wait(palillo[(i+1) mod 5]); wait(palillo[i]); come; signal(palillo[i]); signal(palillo[(i+1) mod 5]; process type filosofo_impar(i:integer); piensa; wait(palillo[i]); wait(palillo[(i+1) mod 5]); come; signal(palillo[i]); signal(palillo[(i+1) mod 5]; IMPLEMENTACIÓN DE SEMAFOROS: Para implementar un semáforo se debe tener en cuenta dos aspectos: 1. El tipo de dato necesario para representar un semáforo. 2. El contenido de las operaciones que se realizan sobre los semáforos. Implementación de semáforos con variables enteras: Un semáforo podemos definir como un registro la siguiente estructura: type semaphore=record of valor:integer; L:lista de proceso End; -11
12 Cada semáforo tiene asociado un valor entero y la lista de procesos que están bloqueados en el semáforo. Cuando un proceso tiene que esperar en un semáforo se añade a la lista de procesos. Cada proceso tiene un único identificador. Una operación signal eliminará un proceso de la lista de procesos si no está vacía. Teniendo en cuenta esta estructura, las operaciones sobre semáforos se pueden definir como: Procedure initial (var s: semaphore; s0:integer); s.valor:=s0; inicializar(s.l); procedure wait(var s:semaphore); s.valor :=s.valor-1; if s.valor<0 then añadir proceso a s.l; bloquearlo; procedure signal(var s:semaphore); s.valor:=s.valor+1; if s.valor<=0 then eliminar un proceso de s.l; desbloquearlo; Las operaciones bloquear y desbloquear son suministrada por el sistema operativo en forma de llamadas al sistema. En esta implementación, los semáforos pueden tener valores negativos, si el valor es negativo, su magnitud será el número de procesos esperando en ese semáforo. Esto ocurre como resultado de intercambiar el orden del decremento y el test en la implementación de la operación wait. La lista puede ser implementada fácilmente por medio de un campo de enlace en cada bloque de control de proceso (pcb), como una cola de estructura fifo. Las operaciones definidas sobre los semáforos se ejecutan indivisiblemente (dos procesos no pueden ejecutar wait y signal sobre el mismo semáforo simultáneamente) esta situación de exclusión mutua se puede resolver de la siguiente manera: 1. En un entorno uniprocesador podemos deshabilitar las instrucciones durante el tiempo que se ejecuten wait y signal. Es posible porque el mecanismo de inhibición de interrupciones no es usa nivel de usuario, sino en la implementación de las operaciones disponibles para el usuario. 2. En un entorno multiusuario, si le hardware no facilita una instrucción especial, se podrá usar cualquier solución software adecuada al problema de sección crítica. De esta forma se puedo eliminar la espera improductiva en la entrada a la sección crítica de los programas de aplicación, limitando a las secciones críticas de las operaciones wait y signal, la espera improductiva son cortas. IMPLEMENTACIÓN DE SEMÁFOROS COMO VARIABLES ENTERAS NO NEGATIVAS: La estructura que representa al semáforo será la misma, pero se modifica la implementación de las operaciones: type semaphore=record of valor:integer; L:lista de proceso End; Procedure initial (var s: semaphore; s0:integer); -12
13 s.valor:=s0; inicializar(s.l); procedure wait(var s:semaphore); if s.valor>0 then s.valor :=s.valor-1; else inserter proceso a s.l; bloquearlo; procedure signal(var s:semaphore); if not vacia(l) then eliminar un proceso de s.l; desbloquearlo; end else s.valor:=s.valor+1; Sincronización en java Java no tiene semáforos como primitivas de sincronización, pero proporciona primitivas con las cuales implementar el comportamiento de semáforo. A continuación veremos como solucionar los problemas de exclusión mutua y condición de sincronización en Java. Exclusión mutua en Java: En java un objeto no está protegido. Cualquier hilo puede hilo puede estar ejecutando código dentro del objeto. La exclusión mutua se consigue mediante la palabra reservada syncronized, y puede ser aplicada a métodos enteros como a bloques de código dentro de un método. Synchronized como modificador del método: Todos los métodos que lleven el modificador syncronized se ejecutarán en exclusión mutua y se garantiza que ningún otro método sincronizado podrá ejecutarse. Sin embargo cualquier método no sincronizado puede estar ejecutándose dentro del objeto. Aquellos threads que quieran ejecutar un método sincronizado, mientras otro thread está dentro de un método sincronizado, tendrá que esperar a que este último abandone la exclusión mutua (la razón natural es la finalización de la ejecución del método aunque puedan existir otras). Ejemplo: puede haber un thread ejecutando el método 2 o 4 T6 T1 T5 T7 m1 m2 m3 m4 m5 Public class Sincronizados{ Public void m1(){ Public synchronized void m2(){ Public void m3(){ Public synchronized void m4(){ Public void m5(){ Synchronized aplicando a un bloque de código Synchronized necesita hacer referencia a un objeto para utilizarlo en un bloque de código y no en un método. En el siguiente ejemplo, se aplica sobre el mismo objeto sobre el que se está invocando m1(). Esto hace que ese trozo de código se ejecute en exclusión mutua con cualquier otro bloque de código sincronizado del mismo objeto, incluído los métodos que lleven el modificador syncronized: Public class Sincronizados2{ Public void m1(){ // Cualquier código sera no sincronizado synchronized (this){ T2 T4 T3-13
14 // Solo esta parte es sincronizada // Cualquier código sera no sincronizado Es posible aplicar synchronized sobre otro objeto distinto a aquel en el que se está utilizando, en el siguiente ejemplo antes de ejecutar el código que está dentro de synchronized se adquiere el cerrojo sobre el objeto otroobjeto. Para adquirirlo ninguno otro thread debe tenerlo en ese momento. public class sincronizados2{ object otroobjeto =new Object(); public void m1(){ // Cualquier código será no sincronizado synchronized (otroobjeto){ // solo esta parte es sincronizada, pero con el cerrojo de otroobjeto // Cualquier código será no sincronizado Esta variante es útil cuando se quiere realizar más de una operación en forma atómica sobre un objeto. (ejemplo: si se quiere hacer un reintegro de una cuenta bancaria y antes consultar el saldo para ver si la operación es factible. Ambas acciones deben ejecutarse sin que se intercale ninguna otra. Primero adquirimos el cerrojo sobre el objeto cuentabancaria y luego realizamos las operaciones que queramos de forma segura. synchronized (cuentabancaria){ if (cuentabancaria.haysaldo(cantidad)) cuentabancaria.reintegro(cantidad); Synchronized sobre métodos static También existe un cerrojo a nivel de clase. Synchronized puede ser usado sobre métodos static, de forma que se puede proteger el acceso de varios threads a variables static. También puede ser usado dentro del código de la siguiente forma: synchronized (nombreclase.class),- El caso de la variable volatile Las operaciones de asignación sobre variables de tipos primitivos menores de 32 bits, se realizan en forma atómica. Pudiendo omitir synchronized eliminando la penalización en el rendimiento que implica su uso. Sin embargo hay que tener cuidado en situaciones como las siguientes: class Ejemplo{ public void cambiarvalor(){ valor=true; Public synchronized void esperaporvalorcierto(){ Valor=false; // otro thread llama al método valor() If (valor){ // puede que este código no se ejecute aunque valor sea true Esto es así porque la MVJ puede hacer algunas modificaciones. Como en el método esperaporvalorcierto() se hace valor=false, el compilador puede suponer que la condición del if nunca se va a dar y considerarlo como código muerto que no se ejecutará. -14
15 La palabra reservada volatile sobre un identificador le dice al compilador que otro thread puede cambiar su valor como volatile. Condición de sincronización en JAVA Synchronized proporciona mecanismos de seguridad e integridad. Sin embargo hay que tener en cuenta la sincronización y comunicación entre los hilos. Java proporciona 3 métodos para las esperas por ocurrencia de eventos y notificaciones: wait(), notify() y notifyall(): wait(): le indica al hilo en curso que abandone la exclusión mutua sobre el objeto (el cerrojo) y se vaya al estado de espera por wait hasta que otro hilo lo despierte mediante notify() o notifyall(). El lugar donde se queda esperando el hilo recibe el nombre de conjunto de espera o wait set. notify(): un hilo arbitrario del conjunto de espera es seleccionado por el planificador para pasar al estado listo. notifyall(): todos los hilos del conjunto de espera son puestos en el estado listo. Estos métodos están definidos en la clase Object y, por lo que son heredados por todas las clases de forma implícita. Ejemplos: Productor/consumidor: En la clase Buffer se utiliza una guarda booleana para asegurarnos de que no se toma un elemento cuando el buffer está vacío y que no se pone un elemento cuando el buffer está lleno. Al final de los métodos tomar y poner se despierta a los posibles hilos dormidos en el conjunto de espera, hay que hacer un notifyall, o no podemos asegurar que ese hilo vaya a satisfacer su condición. Este problema podemos solventarse haciendo uso de las variables de condición. En este caso, el buffer es implementado como una pila. Clase buffer: public class Buffer{ // no es un thread private int cima,capacidad,vector[]; buffer (int i){ cima =0; capacidad=i; vector=new int [i]; synchronized public int extraer(){ while (cima==0) try{ wait(); catch (InterruptedException e){; NotifyAll(); Return vector[--cima]; synchronized public void insertar(int elem){ while (cima==capacidad-1) try{ wait(); catch (InterruptedException e){; vector[cima]=elem; cima++; notifyall(); Clase consumidor public class Consumidor extends Thread { -15
16 int elem; Buffer buffer; Consumidor (Buffer b, int i) { buffer=b; public void run(){ try{ elem=buffer.extraer(); catch (Exception e) { return; Clase Productor public class Productor extends Thread { buffer buffer; int elem; Productor (Buffer b, int i) { elem=i; buffer=b; System.out.println ( entra el productor +i); public void run(){ try{ buffer.insertar(elem); catch (Exception e) { System.out.println ( he puesto el elemento +elem); return; Clase con el programa principal public class ProductorConsumidor { static Buffer buf=new Buffer(3); public static void main(string[] args){ for (int i=1;i<=5;i++) new Productor (buf, i).start(); for (int j=1;j<=5;j++) new Consumidor (buf,j).start(); System.out.println ( Fin del hilo main ); Ejemplo de lectores y escritores: Clase Escritor public class Escritor extends Thread { int miid; Recurso recurso; public Escritor(Recurso _recurso,int _miid){ miid= _miid; recurso= _recurso; public void run(){ int i=0; while(i<10){ System.out.println ( Escritor +miid+ quiere escribir ); Recurso.escribir(); System.out.println ( Escritor +miid+ ha terminado ); i++; -16
17 Clase Lector public class Lector extends Thread { int miid; Recurso recurso; public Lector(Recurso _recurso,int _miid){ miid= _miid; recurso= _recurso; public void run(){ int i=0; while(i<10){ System.out.println ( Lector +miid+ quiere Leer ); Recurso.leer(); System.out.println ( Lector +miid+ ha terminado ); i++; Clase Recurso Esta clase implementa el recurso al que se quiere accede con la política de lectores y escritores. Podemos observar cómo hay partes que están sincronizadas y otras no lo están para permitir un acceso concurrente de lectores. public class Recurso{ int numlectores=0; boolean hayescritor=false; public Recurso (){ public void leer(){ // protocolo de entrada Synchronized (this){ while (hayescritor) try { wait(); catch (Exception e){ numlectores++; // leyendo. Sin sincronizar para permitir concurrencia. // Protocolo de salida Synchronized (this){ numlectores--; if(numlectores==0) notifyall(); synchronized public void escribir(){ // protocolo de entrada synchronized(this){ while(hayescritor (numlectores>0)) try{ wait(); catch(exception e) (e.printstacktrace(); hay escritot=true; // escribiendo. Sin sincronizar, pero solo habrá un escritor. //protocolo de salida -17
18 synchronized (this){ hayescritor=false; notifyall(); Clase con el programa principal public class LyE{ public static void main(string args[]) { Recurso recurso=new Recurso(); for(int i=0;i<3;i++) new Lector (recurso, i).start(); for(int i=0;i<3;i++) new escritor (recurso, i).start(); IMPLEMENTACIÓN DE SEMÁFOROS CON LAS PRIMITIVAS DE JAVA. A continuación veremos cómo implementar un semáforo binario y uno de propósito general usando las primitivas propias de java. La ventaja de Java con respecto a los semáforos es que sus primitivas son más fáciles de utilizar y no están dispersas por el código de los objetos clientes, sino centradas en los objetos que juegan un papel de servidores con lo que el código se hace más fácilmente modificable. Sin embargo se podría hacer uso del paquete semáforo que se implementa a continuación para sincronizar los programas en JAVA. Utilizaremos nombres en mayúsculas para WAIT() y SIGNAL() para evitar confusiones con el wait() propio de Java. Implementación de semáforo binario: package Semaforo; public class SemaforoBinario { protected int contador=0; public SemaforoBinario (int valorinicial){ contador=valorinicial; synchronized public void WAIT(){ while (contador==0) try{ wait(); catch(exception e) { contador--; synchronized public void SIGNAL(){ contador=1; notify();/* aquí con despertar a uno es suficiente, pues todos esperan la misma condición*/ Implementación de semáforo general: Heredamos de la clase anterior, redefiniendo el método SIGNAL() pues ahora el contador puede pasar de uno. package Semaforo; public class SemaforoGeneral extends SemaforoBinario { public SemaforoGeneral (int valorinicial){ super (valorinicial); synchronized public void SIGNAL(){ contador++; notify(); -18
19 Puede observarse que estas implementaciones no nos garantizan una política FIFO para la gestión de procesos bloqueados. Queda como tarea planteada diseñar ambos tipos de semáforos que sigan una política FIFO. Como idea se sugiere la creación de un vector donde cada celda es un hilo. Cada vez que un hilo se bloquea, se añade al final de este vector. Un hilo se desbloqueará cuando sea el primero de este vector. Entonces también se eliminará el hilo del vector. El vector se declararía como: Vector bloqueados=new Vector[50]; // 50 sería el número máximo de procesos bloqueados. Cada vez que un hilo dentro de la operación WAIT() haría algo como: try{ bloqueados.addelement (Thread.concurrentThread()); do{ wait(); /* la condición de salida es que este thread sea el que más tiempo lleva esperando en el semáforo*/ condsalida=bloqueados.firstelement().equals (Thread.concurrentThread()); // si este thread no puede despertarse, se despierta a otro If (!condsalida) notify(); while(!condsalida); condsalida=false; bloqueados.removeelement(thread.concurrentthread()); catch (Exception e) { Inconvenientes del mecanismo de los semáforos: 1. Es un mecanismo de bajo nivel, no estructurado. la ejecución de cada sección crítica debe comenzar con un wait y terminar con un signal sobre el mismo semáforo, o podrían tener efectos no deseables, como no asegurar una ejecución en exclusión mutua de secciones críticas. 2. No se puede restringir el tipo de operaciones realizadas sobre los recursos. 3. Cuando se usan semáforos, un programador puede olvidar incluir en las secciones críticas todas las sentencias que hagan referencia a los objetos compartidos. 4. Los programas que utilizan semáforos son difíciles de mantener, ya que el código de sincronización está repartido entre los distintos procesos, con lo que cualquier modificación implica la revisión de todos los procesos. -19
20 Regiones críticas condicionales (RCC): Constituyen un mecanismo estructurado que nos va a permitir diferenciar el control de acceso a la sección crítica, de la implementación de las condiciones sincronizadas. Definición: el uso de las regiones críticas condicional hace que el compilador imponga determinadas restricciones al uso de variables compartidas, va a ser detectado en tiempo de compilación. Esta propiedad nos llevará a diseñar programas más estructurados y fáciles de mantener Para conseguir que el compilador pueda detectar el uso incorrecto de variables compartidas, esas tienen que ser declaradas de una forma especial (además de ser declaradas de forma normal). Para ello se emplea la instrucción resource de la siguiente forma: Var i,j: integer; Resource SC: i,j; La declaración de un recurso (resource) consta de dos elementos: el nombre del recurso, en este caso SC, y las variables que lo componen, las variables enteras i y j. la única restricción que imponen es que una misma variables no puede pertenecer a mas de un recurso. De esta forma, todas las variables compartidas. Al haber definido las variables compartidas de una forma especial, estas deber ser accedidas de una forma especial utilizando la construcción región: Región identificar do S1;. Sn; End; Donde identificador se corresponde con el nombre del recurso al que pertenecen las variables compartidas a las que vamos a acceder. Por ejemplo, teniendo en cuenta la declaración de variables anterior, para poder incrementar la variable i deberíamos escribir el siguiente código: Region SC do I:=i+1; El uso de la RCC, nos garantiza que el código situado dentro de ella se ejecuta en exclusión mutua con el resto de RCC. Para ello, cada vez que un proceso requiera ejecutar una región, primero se debe comprobar si ésta no esta siendo accedida por otro proceso. Si se encuentra libre, el proceso en cuestión puede ejecutar la región. Caso contrario, se queda bloqueado en la cola principal junto con el resto de los procesos que están esperando por acceder a la región. Existe una única cola principal por definición de recurso. Cuando un proceso termina la ejecución de una región, este le cede el paso al proceso que está en el frente de la cola principal, y si esta está vacía, la región queda libre. Se debe tener cuidado en utilizar distintas regiones anidadas para evitar caer en interbloqueo. En el siguiente ejemplo, puede observarse que ambos procesos llegan a una situación de interbloqueo al ejecutar la segunda región, ya que ambos casos la exclusión mutua de la correspondiente región ha sido adquirida por el otro proceso. Tenemos dos -20
21 procesos bloqueados en espera de un evento que nunca se va a producir (la liberación de la correspondiente región). process p1; región A do región B do s; end (*p1*); process p2; region B do region A do s; end (*p2*); Como podemos ver, las RCC: 1- Proporcionan: un mecanismo potente para el control de exclusión mutua, y es el compilador quien de forma automática coloca los wait y signal necesarios, impidiendo que el programador se equivoque. 2- Permiten resolver el problema de la implementación de las condiciones de sincronización. Podemos utilizar las RCC de la siguiente forma: Region identificador when cond do End; S1;. Sn; La condición booleana cond permite implementar condiciones de sincronización, garantizándose la exclusión mutua en la evaluación de la condición. La ejecución de una RCC se realiza de la siguiente forma: 1- Antes de entrar a la región, el proceso debe conseguir el acceso en exclusión mutua a la región. De lo contrario queda bloqueado en la cola principal. 2- Si el proceso consigue el acceso evalúa la condición, si es verdadera el proceso puede ejecutar las instrucciones de la región (s1,sn). Si la condición es falsa, el proceso libera la exclusión mutua de la región y queda bloqueado en la cola asociada a la condición de la región, la cola de eventos. 3- Cuando el proceso termina, primero comprueba si puede desbloquear, y ceder la exclusión mutua, a alguno de los procesos que están bloqueados en la cola de eventos (implica una reevaluación de la condición de los procesos). Si ninguno de los procesos de la cola de eventos puede ser desbloqueado (condición negativa), se cede la exclusión mutua al primer proceso de la -21
22 cola principal. Si no existe tal proceso, la región quedará libre hasta que u proceso quiera acceder a ella. Los proceso bloqueados en la cola de eventos tienen prioridad sobre los que están bloqueados en la cola principal (los procesos bloqueados en la cola de eventos ya consiguieron la exclusión mutua para acceder a la evaluación de la variable condición por lo que tienen prioridad sobre los que están luchando por conseguir el acceso exclusivo a la región por primera vez). Ejemplo: implementar un semáforo mediante RC, 1. Debemos determinar cuáles son las variables compartidas. En el caso de semáforos, necesitamos una púnica variable entera compartida que hará de contador. 2. Debemos determinar cuáles son las condiciones bajo las cuales se puede acceder a la variable compartida: a. El decremento de la variable compartida en el wait solo es posible cuando el valor de la variable es mayor a cero. b. El incremento de la variables compartida en la operación signal siempre es posible, pero siempre debe hacerse en exclusión mutua. Bajo estas consideraciones una implementación posible sería: program semáforo; var s: integer; resource sem: s; procedure wait; (* si s=0 el proceso quedará bloqueado en la cola de condición *) region sem when s>0 do -22
23 s:=s-1; procedure signal; region sem do s:=s+1; s:=0; Resolución de problemas usando regiones críticas condicionales 1. Problema del productor /consumidor con buffer limitado: primero se debe determinar que elementos constituyen las secciones críticas que deben ser protegidas, para luego determinar las condiciones a establecer para el acceso a dichas regiones. Considerando un esquema donde existan varios productores y consumidores, las variables que van a compartir mas de un proceso y debemos proteger mediante RCC son: - Punteros de acceso al buffer, cola y frente (porque varios procesos pueden extraer e insertar elementos al mismo tiempo). - Un contador de elementos en el buffer, elementos, que es actualizado al insertar o extraer un elemento y ayudará a definir las condiciones de sincronización. Establecidas las RC, se establece las condiciones de sincronización entre productores consumidores, que son: - Los productores no pueden acceder al buffer cuando este está lleno, elementos =n - Los consumidores no pueden acceder al buffer cuando este está vacío. Elementos =0 Una posible solución sería: program productor/consumidor; const nproc=6; n=10; var elementos, cola, frente, i: integer; recurso: array [0..n-1] of item; resource buffer: cola, frente, recurso, elementos; process type productor; producir un item; (* si el buffer está lleno hay que esperar a que se libere un hueco*) region buffer when elementos <n do recurso[frente]:=item; frente:=(frente+1) mod n; elementos :=elementos +1; -23
24 process type consumidor; (* si el buffer esta vacío hay qye esperar que se inserte un elementos*) región buffer when elementos > 0 do item:=buffer[cola]; cola:= (cola +1) mod n; elementos:= elementos -1; consumir el item; var prod:= array [0..nproc-1] of productor; cons:= array [0..nproc-1] of consumidor; elementos:=0; cola:= 0; frente:=0; co for i:=0 to nproc do prod[i]; cons[i], coend end. Se puede apreciar, que las variables frente, cola y elementos constituyen sección crítica, y cuáles son las condiciones de sincronización. De esta forma, con las RCC, se consiguió en forma explícita controlar el acceso en exclusión mutua a las secciones críticas y de forma explícita se estableció las condiciones de sincronización para acceder a dichas secciones. Con el las RCC, se consiguió mayor legibilidad en los programas concurrentes 2. El Problema de los lectores y escritores Como se pudo ver anteriormente, este problema admite varias soluciones, que depende de la política de acceso al recurso. Veremos dos variantes de este problema: - Prioridad en la lectura, los lectores pueden acceder siempre al recurso, salvo que algún escritor tenga el acceso. - Prioridad de escritura: cuando un escritor esté esperando para acceder al recurso, os lectores deben esperar hasta que dicho escritor haya podido acceder al recurso. Ambas políticas son válidas, siempre y cuando que se permita a los lectores acceder concurrente al recurso compartido. -24
25 a) Prioridad de lectura: es necesario llevar la cuenta del número de lectores que concurrentemente están accediendo al recurso n1. Esta variable es accedida por escritores y lectores con lo que formará parte de la sección crítica. Las condiciones de sincronización serían: - Los lectores pueden acceder al recurso siempre que un escritor no esté escribiendo. - Los escritores solo pueden acceder al recurso cuando no hayan lectores en el recurso n1=0 La solución sería: program lectores/escritores; const nlector=10; nescritor=5; var n1,i:integer; resource datos: n1; process type lector (i:integer); (*los lectores siempre acceden al recurso*) región datos do n1:=n1+1; leer del recurso; región datos do n1:=n1-1; (* lector*) process type escritor (i:integer); (* los escritores deben esperar a que no haya lectores*) región datos when n1=0 do escribir en el recurso; (*escritor*) var lec: array[1..nlector] of lector; esc: array[1..nscriptor] of escritor n1:=0; co for i:=0 to nlector do lector[i] (i); for i:=0 to nescritor do escritor[i] (i); coend end. Se puede observar que parte de código corresponde con la sección crítica y cuáles son las condicione de sincronización, siendo esta solución es más clara que la implementada con semáforos. Además se solucionaron en forma implícita los protocolos de salida del escritor, ya que si tenemos en cuenta el funcionamiento de las RCC cuando un escritor finalice su acceso al recurso se intentará en primer lugar desbloquear a algún proceso bloqueado en la condición n1=0; es decir, intentará desbloquear a un escritor. Si no existe un escritor bloqueado, se intentará desbloquear a un lector que esté -25
26 esperando acceder al recurso en exclusión mutua. Puede observarse que se resolvió implícitamente, la activación en cadena de los lectores para garantizar el acceso concurrente al recurso. b) Prioridad en la escritura: los lectores deben ser bloqueados si hay un escritor esperando para acceder al recurso, cuando un escritor desee acceder al recurso, ningún lector puede acceder, de tal forma que cuando los lectores que ya estaban accediendo al recurso terminen, se atiende la petición del escritor. Para implementar esta política de acceso vamos a necesitar un nuevo contador, nee, que nos indique el número de escritores que están esperando por acceder al recurso, y un variable booleana, escribiendo, que nos indique cuando el recurso está siendo accedido para escritura. Una solución sería: Program lectores/escritores; Const N lector=10; Nescritor=5; Var N1,nee,i:integer; Resource datos:n1; Process type lector (i:integer); (*los lectores deben esperar si hay algún escritor escribiendo o en espera*) Región datos when not escribiendo and nee =0 do N1:=n1+1; Leer del recurso; Región datos do N1:=n1-1; End; (*lector*) Process type escritor (i:integer); (*los escritores deben esperar si hay otro escritor o hay algun lector*) Región datos when n1=0 and not escribiendo do.escribiendo:=true; Nee:=nee-1; End; Escribiendo en el recurso; Región datos do.escribiendo:=false; End; (*escritor*) Var Lec: array[1..nlector] of lector; Esc: array[1..nscritor] of escritor; N1:=0; Escribiendo:=false Co For i:=0 to nlector do Lector[i] (i); For i:=0 to nescritor do Escritor [i] (i); Coend End. -26
PROGRAMACION CONCURRENTE
PROGRAMACION CONCURRENTE II.3 Sincronización basada en memoria compartida: Semáforos J.M. Drake 1 Procesos concurrentes y memoria compartida. Si los diferentes procesos de un programa concurrente tienen
Más detallesConcurrencia entre Procesos.
Concurrencia entre Procesos. Sistemas Operativos Tema 3. 1 Procesamiento concurrente. Procesamiento concurrente: base de los sistemas operativos modernos (multiprogramados): Un conjunto de procesos que
Más detallesUnidad Didáctica 2. Elementos básicos del lenguaje Java Tipos, declaraciones, expresiones y asignaciones
Unidad Didáctica 2 Elementos básicos del lenguaje Java Tipos, declaraciones, expresiones y asignaciones Fundamentos de Programación Departamento de Lenguajes y Sistemas Informáticos Versión 1.0.3 Índice
Más detallesTema 3: Concurrencia de procesos
Tema 3: Concurrencia de procesos Yolanda Blanco Fernández yolanda@det.uvigo.es Concurrencia, Tiempo Real y Paralelismo Concurrencia: Convivencia de un conjunto de procesos en un mismo ordenador. Sistemas
Más detallesCarlos Montenegro. Programación Orientada a Objetos Proyecto Curricular de Ingeniería de Sistemas
2 - Introducción al lenguaje Java, identificadores y comentarios. Carlos Montenegro Programación Orientada a Objetos Proyecto Curricular de Ingeniería de Sistemas 1. Introducción: Java tiene como todos
Más detalles2.2 Nombres, Ligado y Ámbito
2.2 Nombres, Ligado y Ámbito Ligado estático y dinámico, reglas de ámbito y prueba de tipos. Conceptos Nombres e Identificadores Variables Tipos Ámbito Constantes Nombres Identificador que designa en el
Más detallesProgramación Concurrente en Java: Threads. Ejemplos de programación concurrente. Luis Fernando Llana Díaz. 24 de abril de 2008
Departamento de Sistemas Informáticos y Computación Universidad Complutense de Madrid de abril de 00 Ejemplos de programación concurrente En un sistema operativo, diversos programas compiten por los recursos
Más detallesMONITORES EN JAVA. Antonio Tomeu Control de la Concurrencia en Java: API Estándar
MONITORES EN JAVA Un monitor es un objeto que implementa acceso bajo e.m. a todos sus métodos, y provee sincronización En Java, son objetos de una clase cuyos métodos públicos son todos synchronized Un
Más detallesTest : Conteste exclusivamente en una HOJA DE LECTURA ÓPTICA, no olvidando marcar que su tipo de examen es A.
SISTEMAS INFORMÁTICOS I Junio 2003 INGENIERÍA EN INFORMÁTICA - Código Carrera 55 - Código Asignatura 077 Tipo de Examen: A NO SE PERMITE EL USO DE NINGÚN MATERIAL Tiempo: 2 horas Apellidos: Nombre: DNI:
Más detallesManipulación de procesos
Manipulación de procesos Las primeras computadoras solo podían manipular un programa a la vez. El programa tenía control absoluto sobre todo el sistema. Con el desarrollo vertiginoso del hardware ese panorama
Más detallesImplementación de monitores POSIX
Implementación de monitores POSIX Ampliación de Sistemas Operativos (prácticas) E.U. Informática en Segovia Universidad de Valladolid Programación concurrente: Problemática Presencia de condiciones de
Más detallesSistemas operativos. Hasta ahora hemos visto. Relación programa-sistema operativo Gestión de memoria
Sistemas operativos UPCO ICAI Departamento de Electrónica y Automática 1 Hasta ahora hemos visto Relación programa-sistema operativo Gestión de memoria Reserva para la ejecución Pilas, heap, memoria de
Más detallesVariables. Una variable no es más que un nombre simbólico que identifica una dirección de memoria: vs.
Variables Una variable no es más que un nombre simbólico que identifica una dirección de memoria: Suma el contenido de la posición 3001 y la 3002 y lo almacenas en la posición 3003 vs. total = cantidad1
Más detallesDesde los programas más simples escritos en un lenguaje de programación suelen realizar tres tareas en forma secuencial.
Tipos de Datos Desde los programas más simples escritos en un lenguaje de programación suelen realizar tres tareas en forma secuencial. Entrada de datos Procesamientos de datos Salida de resultados Los
Más detallesFUNDAMENTOS DE INFORMÁTICA
FUNDAMENTOS DE INFORMÁTICA Tema 1 Introducción a la Programación en Visual Basic Departamento de Ingeniería de Sistemas y Automática Universidad de Vigo undamentos de Informática. Departamento de Ingeniería
Más detallesManual de turbo pascal
Universidad Nacional Experimental De Los Llanos Occidentales Ezequiel Zamora UNELLEZ-Barinas Manual de turbo pascal Bachilleres: Martinez Ninibeth C.I:20.867.002 Mora Yaco C.I:17.205.073 Estructura de
Más detallesEl problema de los Filósofos
El problema de los Filósofos Problemas de Programación Concurrente Solución con Semáforos Para evitar una situación de interbloqueo se limita el número de filósofos en disposición de comer a 4. PROGRAM
Más detallesArrays unidimensionales. Dim.Option Base. Erase. Ejemplos en Visual Basic (CU00311A)
aprenderaprogramar.com Arrays unidimensionales. Dim.Option Base. Erase. Ejemplos en Visual Basic (CU00311A) Sección: Cursos Categoría: Curso Visual Basic Nivel I Fecha revisión: 2029 Autor: Mario R. Rancel
Más detallesConcurrencia: deberes. Concurrencia: Exclusión Mutua y Sincronización. Concurrencia. Dificultades con la Concurrencia
Concurrencia: deberes Concurrencia: Exclusión Mutua y Sincronización Capítulo 5 Comunicación entre procesos Compartir recursos Sincronización de múltiples procesos Asignación del tiempo de procesador Concurrencia
Más detallesReceta general para resolver problemas de sincronización con semáforos
Receta general para resolver problemas de sincronización con semáforos La primera vez que te enfrentas a la tarea de implementar una solución a un problema de sincronización entre procesos, es normal que
Más detallesTECNICO SUPERIOR EN INFORMÁTICA EMPRESARIAL MÓDULO INTRUCCIONAL
1 TECNICO SUPERIOR EN INFORMÁTICA EMPRESARIAL MÓDULO INTRUCCIONAL TECNOLOGÍA DE LA COMPUTADORA FACILITADOR: PARTICIPANTE: DAVID, CHIRIQUÍ 2015 2 Qué es un programa? Un programa informático es un conjunto
Más detallesMétodos que devuelven valor Dado el siguiente triángulo rectángulo:
Métodos que devuelven valor Dado el siguiente triángulo rectángulo: hipotenusa altura base Para dibujar este triángulo necesitamos los siguientes datos: base y altura La base y la altura, se utilizarán
Más detalles1. Cuántas sentencias hay en la secuencia principal del siguiente programa?
1. Cuántas sentencias hay en la secuencia principal del siguiente programa? public class PruebaSwitch { System.out.print ("Opcion: "); case 3: System.out.println ("miércoles "); A. 1. B. 4. C. Más de 10.
Más detallesPROGRAMACIÓN CONCURRENTE. Tema 5 Monitores
PROGRAMACIÓN CONCURRENTE Tema 5 Monitores 1 Indice Definición de los monitores Sincronización condicional usando monitores Algunos problemas con monitores 2 Problemas de las regiones críticas condicionales
Más detallesCDI Exclusión mutua a nivel alto. conceptos
conceptos El concepto de usar estructuras de datos a nivel alto libera al programador de los detalles de su implementación. El programador puede asumir que las operaciones están implementadas correctamente
Más detallesQué es un programa informático?
Qué es un programa informático? Un programa informático es una serie de comandos ejecutados por el equipo. Sin embargo, el equipo sólo es capaz de procesar elementos binarios, es decir, una serie de 0s
Más detallesTodo programa en 'C' consta de una o más funciones, una de las cuales se llama main.
LENGUAJE C CARACTERISTICAS DEL LENGUAJE 'C' El lenguaje 'C' se conoce como un lenguaje compilado. Existen dos tipos de lenguaje: interpretados y compilados. Los interpretados son aquellos que necesitan
Más detallesUnidad II: Análisis semántico
Unidad II: Análisis semántico Se compone de un conjunto de rutinas independientes, llamadas por los analizadores morfológico y sintáctico. El análisis semántico utiliza como entrada el árbol sintáctico
Más detallesTEMA 7: Ficheros. TEMA 7: Ficheros. 7.1.-Concepto de fichero
TEMA 7: Ficheros 7.1.-Concepto de fichero Todas las estructuras de datos que hemos visto hasta ahora utilizan memoria principal. Esto tiene dos limitaciones importantes: 1. Los datos desaparecen cuando
Más detallesTEMA 5: Control de la Concurrencia en Java (API Estándar)
TEMA 5: Control de la Concurrencia en Java (API Estándar) CONTENIDO Exclusión Mutua con código synchronized. Exclusión Mutua con métodos synchronized. Protocolos de Control de la Exclusión Mutua. Interbloqueos
Más detallesSistemas Operativos. Daniel Rúa Madrid
Sistemas Operativos Daniel Rúa Madrid Qué es? Es un programa que administra el hardware de una computadora. También proporciona las bases para los programas de aplicación y actúa como intermediario entre
Más detallesIntroducción a las sentencias de control
INSTRUCCIONES DE CONTROL CONTENIDOS 1. Introducción a las sentencias de control. 2. Instrucciones o sentencias condicionales: IF, IF-ELSE, SWITCH. 3. Instrucciones o sentencias repetitivas o iterativas:
Más detallesINTRODUCCIóN A LA PROGRAMACIóN APUNTES DE JAVA APUNTES DE JAVA
APUNTES DE JAVA FUNCIONAMIENTO DE UN PROGRAMA Assembler Ensamblador Ejecuta Programador Programa fuente BASIC Interprete Ejecuta C, C++, Pascal Compilador Compila Ejecuta Programa fuente Programa Objeto
Más detallesMensajes. Interbloqueo
CONCURRENCIA DE PROCESOS Preparado por: Angel Chata Tintaya (angelchata@hotmail.com) Resumen Los procesos comparten variables globales, comparten y compiten por recursos, se ejecutan simultáneamente intercalándose
Más detallesConcurrencia. Primitivas IPC con bloqueo
Concurrencia Primitivas IPC con bloqueo Primitivas de IPC con bloqueo La solución de Peterson es correcta, pero tiene el defecto de requerir espera ocupada: Cuando un proceso quiere entrar en su región
Más detallesLA ESTRUCTURA DE DATOS PILA EN JAVA. CLASE STACK DEL API JAVA. EJEMPLO Y EJERCICIOS RESUELTOS. (CU00923C)
APRENDERAPROGRAMAR.COM LA ESTRUCTURA DE DATOS PILA EN JAVA. CLASE STACK DEL API JAVA. EJEMPLO Y EJERCICIOS RESUELTOS. (CU00923C) Sección: Cursos Categoría: Lenguaje de programación Java nivel avanzado
Más detallesNormalmente, los programas son ejecutados de forma secuencial. Único flujo de control
Hilos BUAP Introducción Normalmente, los programas son ejecutados de forma secuencial Único flujo de control Un programa con un único flujo de control, ejecuta sólo una tarea (hilo) Dr. Ivan Olmos 2 Introducción
Más detallesConstruyendo Programas más Complejos
Arquitectura de Ordenadores Construcciones de Alto Nivel en Ensamblador Abelardo Pardo abel@it.uc3m.es Universidad Carlos III de Madrid Departamento de Ingeniería Telemática Construyendo Programas más
Más detallesIntroducción a Java LSUB. 30 de enero de 2013 GSYC
Introducción a Java LSUB GSYC 30 de enero de 2013 (cc) 2013 Laboratorio de Sistemas, Algunos derechos reservados. Este trabajo se entrega bajo la licencia Creative Commons Reconocimiento - NoComercial
Más detallesMANUAL AB TUTOR CONTROL
MANUAL AB TUTOR CONTROL IES. CARPE DIEM Página 1 INTRODUCCIÓN Qué es AB Tutor Control? AB Tutor Control es un paquete de administración de escritorio. Proporciona al profesor una herramienta para controlar
Más detallesTema 2. El lenguaje JAVA
Tema 2. El lenguaje JAVA Nomenclatura habitual Variables Tipos de variables Tipos primitivos Referencias Arrays Operadores Operadores de Java Precedencia de operadores Sentencias de control Sentencias
Más detallesClase adicional 2. Estructuras básicas de control. Temas
Clase adicional 2 Temas Estructuras de control Sentencia condicional Iteración Clases Definir una clase Crear una instancia de una clase Campos estáticos Problemas de la clase adicional Problema de diseño
Más detallesCiclos. Recordando Estructuras de Control Básicas: SELECCIÓN (condición) SECUENCIAL
Ciclos Fundamentos de Programación Recordando Estructuras de Control Básicas: Una secuencia es una serie de estatutos que se ejecutan uno después de otro. Selección (condición) ejecuta diferentes estatutos
Más detallesAgradecimientos. Nota de los autores. 1 Problemas, algoritmos y programas 1
Prologo Agradecimientos Nota de los autores Índice general I III V VII 1 Problemas, algoritmos y programas 1 1.1 Programas y la actividad de la programación.................... 4 1.2 Lenguajes y modelos
Más detallesTema 3. Monitores Programación Concurrente
Tema 3. Monitores Programación Concurrente Depto. de Lenguajes y Sistemas Informáticos Universidad de Granada Contenidos 1. Concepto de Monitor 1.1. Fundamento teórico de los monitores 1.2. Sintaxis de
Más detallesfundamentos de programación (unidad 4) programación estructurada en Java
fundamentos de programación (unidad 4) programación estructurada en Java Para ver una copia completa de la licencia, acudir a la dirección http://creativecommons.org/licenses/by-nc-sa/2.5/es/legalcode.es
Más detallesCapítulo 1. Sistemas de Asignación Contigua Basados en Particiones
Problemas Resueltos Capítulo 1. Sistemas de Asignación Contigua Basados en Particiones 1.- Notas y criterios para los problemas 2.- NOTA GENERAL: Tema 1 Introducción a la gestión de memoria. 3.- Problemas
Más detallesHP - UX. Qué es HP UX?
HP - UX Integrantes: Cisneros Pedraza Christian. Jiménez Nieves José Manuel. Villanueva Armenta Fernando. Qué es HP UX? Hp UX es una variante de Unix creada por los desarrolladores de software de HP. Provee
Más detallesCAPÍTULO 8. Comunicación y sincronización basada en variables compartidas
CAPÍTULO 8. Comunicación y sincronización basada en variables compartidas 8 Comunicación y sincronización basada en variables compartidas...2 8.1 Exclusión mutua y condición de sincronización....2 8.2
Más detalles4.6.- Integridad: Control de concurrencia.
4.6.- Integridad: Control de concurrencia. 4.6.1.- Introducción 4.6.2.- Técnicas de Bloqueo. 4.6.2.1.- Bloqueo (variable cerrojo) Tipos, protocolos Problemas. Interbloqueo Granularidad 4.6.2.2.- Marcas
Más detallesPrincipios de Computadoras II
Departamento de Ingeniería Electrónica y Computadoras Ing. Ricardo Coppo rcoppo@uns.edu.ar Qué es un Objeto? Un objeto es una instancia de una clase Las clases actuán como modelos que permiten la creación
Más detallesTema 3 SUBRUTINAS. Estructura de Computadores OCW_2015 Nekane Azkona Estefanía
Tema 3 SUBRUTINAS ÍNDICE Definición e instrucciones básicas Soporte para el tratamiento de subrutinas (ejecución de la subrutina y gestión del bloque de activación) Interrupciones vs llamadas a procedimiento
Más detallesPROGRAMACION ORIENTADA A OBJETOS EN C++
PROGRAMACION ORIENTADA A OBJETOS EN C++ 1- INTRODUCCIÓN El lenguaje C++ representa el resultado de los esfuerzos realizados para proporcionar las ventajas de la programación Orientada a Objetos a un lenguaje
Más detallesSISTEMAS INFORMÁTICOS PROGRAMACION I - Contenidos Analíticos Ing. Alejandro Guzmán M. TEMA 2. Diseño de Algoritmos
TEMA 2 Diseño de Algoritmos 7 2. DISEÑO DE ALGORITMOS 2.1. Concepto de Algoritmo En matemáticas, ciencias de la computación y disciplinas relacionadas, un algoritmo (del griego y latín, dixit algorithmus
Más detallesAPUNTADORES. Un apuntador es un objeto que apunta a otro objeto. Es decir, una variable cuyo valor es la dirección de memoria de otra variable.
APUNTADORES Un apuntador es un objeto que apunta a otro objeto. Es decir, una variable cuyo valor es la dirección de memoria de otra variable. No hay que confundir una dirección de memoria con el contenido
Más detallesSOLUCIONES. SISTEMAS OPERATIVOS Examen de la convocatoria extraordinaria de diciembre 2 de diciembre de 2010
Calificación SISTEMAS OPERATIVOS Examen de la convocatoria extraordinaria de diciembre 2 de diciembre de 2010 Nombre SOLUCIONES 1 2 3 4 5 Titulación Dispone de tres horas y quince minutos para realizar
Más detallesFUNDAMENTOS DE INFORMÁTICA
FUNDAMENTOS DE INFORMÁTICA Tema 2 Expresiones, operadores y estructuras de control Departamento de Ingeniería de Sistemas y Automática Universidad de Vigo Fundamentos de Informática. Departamento de Ingeniería
Más detallesTema: Clases y Objetos en C#. Parte II.
Programación II. Guía No. 5 1 Facultad: Ingeniería Escuela: Computación Asignatura: Programación II Tema: Clases y Objetos en C#. Parte II. Objetivos Implementar clases, objetos, propiedades, métodos y
Más detallesThreads. La plataforma JAVA soporta programas multhreading a través del lenguaje, de librerías y del sistema de ejecución. Dos.
Threads Un thread es un flujo de control secuencial dentro de un programa. A los threads también se los conoce como procesos livianos ó contextos de ejecución. Un thread es similar a un programa secuencial:
Más detallesLección 2: Creando una Aplicación en Java. 1. Estructura del archivo de una clase. 3. Definiendo clases fundamentos
Lección 2: Creando una Aplicación en Java 1. Estructura del archivo de una clase 2. Usando una clase 3. Definiendo clases fundamentos Objetivos Conocer: La forma en la cual está se está estructurado el
Más detallesTema 13: Apuntadores en C
Tema 13: Apuntadores en C M. en C. Edgardo Adrián Franco Martínez http://www.eafranco.com edfrancom@ipn.mx @edfrancom edgardoadrianfrancom Estructuras de datos (Prof. Edgardo A. Franco) 1 Contenido Introducción
Más detallesJava para no Programadores
Java para no Programadores Programa de Estudio Java para no Programadores Aprende a programar con una de las tecnologías más utilizadas en el mercado de IT. Este curso está orientado a quienes no tienen
Más detallesmedia = ( temp0 + temp1 + temp2 + temp3 + temp temp23 ) / 24; printf( "\nla temperatura media es %f\n", media );
Arrays en el lenguaje C Introducción Una posible definición de array sería: Un conjunto de datos del mismo tipo, identificados por el mismo nombre, y que se pueden distinguir mediante un número de índice.
Más detallesADMINISTRACION DE LA MEMORIA. En memoria 1 solo proceso Desventajas:
ADMINISTRACION DE LA MEMORIA Función del Administrador de Memoria Registra qué parte de memoria está libre y ocupada Asigna y libera espacio en memoria a los procesos Administra el intercambio entre la
Más detallesEstatutos de Control C# Estatutos de Decisión (Selección)
SELECCIÓN Estatutos de Control C# Estatutos de Decisión (Selección) IF Condición THEN Estatuto1 ELSE Estatuto2 Estatuto1 Statement Condición... Antes de ver esta presentación: Lee el Capítulo correspondiente
Más detallesTEMA 4. ESTRUCTURAS DE CONTROL
M.P. Sesmero, P. de Toledo, F.J. Ordoñez, J. Gómez-Romero, J.A. Iglesias, J.L. Mira Programación TEMA 4. ESTRUCTURAS DE CONTROL Grado en Ingeniería en Tecnologías Industriales Programación CONTENIDOS 4.1.
Más detallesTema 2 Introducción a la Programación en C.
Tema 2 Introducción a la Programación en C. Contenidos 1. Conceptos Básicos 1.1 Definiciones. 1.2 El Proceso de Desarrollo de Software. 2. Lenguajes de Programación. 2.1 Definición y Tipos de Lenguajes
Más detallesGuía práctica de estudio 03: Algoritmos
Guía práctica de estudio 03: Algoritmos Elaborado por: M.C. Edgar E. García Cano Ing. Jorge A. Solano Gálvez Revisado por: Ing. Laura Sandoval Montaño Guía práctica de estudio 03: Algoritmos Objetivo:
Más detallesFunciones básicas del depurador
Funciones básicas del depurador Con frecuencia, los alumnos piensan que cuando su programa no tiene errores de compilación (está correctamente escrito) entonces ya es correcto. Muchas veces esto no es
Más detallesAlgoritmos. Medios de expresión de un algoritmo. Diagrama de flujo
Algoritmos En general, no hay una definición formal de algoritmo. Muchos autores los señalan como listas de instrucciones para resolver un problema abstracto, es decir, que un número finito de pasos convierten
Más detallesBenemérita Universidad Autónoma del Estado de Puebla
Benemérita Universidad Autónoma del Estado de Puebla Facultad de Cs. De la Computación Programación Concurrente y Paralela Práctica de Laboratorio No. 4 Profr: María del Carmen Cerón Garnica Alumno: Roberto
Más detallesEstructuras de Datos Declaraciones Tipos de Datos
Departamento de Informática Universidad Técnica Federico Santa María Estructuras de Datos Declaraciones Tipos de Datos Temas: 2-3-4 IWI-131, paralelo 01 Profesor: Teddy Alfaro O. Lenguaje de Programación
Más detallesEstructuras de control
Estructuras de control Introducción Los algoritmos vistos hasta el momento han consistido en simples secuencias de instrucciones; sin embargo, existen tareas más complejas que no pueden ser resueltas empleando
Más detalles4. Operadores Operador asignación
Programación orientada a objetos con Java 43 4. Operadores Objetivos: a) Describir los operadores (aritméticos, incrementales, de relación, lógicos y de asignación) y los tipos de dato primitivos sobre
Más detallesMétodos para escribir algoritmos: Diagramas de Flujo y pseudocódigo
TEMA 2: CONCEPTOS BÁSICOS DE ALGORÍTMICA 1. Definición de Algoritmo 1.1. Propiedades de los Algoritmos 2. Qué es un Programa? 2.1. Cómo se construye un Programa 3. Definición y uso de herramientas para
Más detallesPROGRAMACIÓN EN JAVA
SISTEMAS INFORMÁTICOS INDUSTRIALES curso 2007-2008 PROGRAMACIÓN EN JAVA PRÁCTICA 3: Comunicación entre tareas. Modelo productor / consumidor. Objetivos Implementar una aplicación en Java en la que existan
Más detallesTema 2 Conceptos básicos de programación. Fundamentos de Informática
Tema 2 Conceptos básicos de programación Fundamentos de Informática Índice Metodología de la programación Programación estructurada 2 Pasos a seguir para el desarrollo de un programa (fases): Análisis
Más detallesTema 14: Sistemas Secuenciales
Tema 14: Sistemas Secuenciales Objetivos: (CONTADORES) Introducción. Características de los contadores. Contadores Asíncronos. Contadores Síncronos. 1 INTRODUCCIÓN Los contadores son sistemas secuenciales
Más detallesINTERFACE COMPARATOR. DIFERENCIAS ENTRE COMPARATOR Y COMPARABLE. CLASE COLLECTIONS. EJERCICIOS RESUELTOS. (CU00918C)
APRENDERAPROGRAMAR.COM INTERFACE COMPARATOR. DIFERENCIAS ENTRE COMPARATOR Y COMPARABLE. CLASE COLLECTIONS. EJERCICIOS RESUELTOS. (CU00918C) Sección: Cursos Categoría: Lenguaje de programación Java nivel
Más detallesCómo configurar formatos Wiegand personalizados
Cómo configurar formatos Wiegand personalizados Muchos sistemas de control de acceso utilizan un formato Wiegand para sus tarjetas de usuario con hasta 50 bits de información almacenada. Es necesario filtrar
Más detallesTEMA 2: Estructuras de Control: Condicionales
UNIVERSIDAD CENTRAL DE VENEZUELA FACULTAD DE CIENCIAS ESCUELA DE MATEMÁTICA INTRODUCCIÓN A LA COMPUTACIÓN TEMA 2: Estructuras de Control: Condicionales Estructuras Condicionales En un algoritmo se tiene
Más detallesTabla de Símbolos. Programación II Margarita Álvarez
Programación II Margarita Álvarez La tabla de símbolos es una estructura global utilizada por distintos módulos del compilador. Es el principal atributo heredado. Almacena todos los nombres declarados
Más detallesProgramación Orientada a Objetos Sentencias Java Parte I Ing. Julio Ernesto Carreño Vargas MsC.
Sentencias Java Parte I Ing. Julio Ernesto Carreño Vargas MsC. Variables Conceptos de Memoria Una variable es un espacio en la memoria del PC Cada variable tiene un nombre, un tipo, un tamaño y un valor
Más detallesUNIVERSIDAD DE LOS ANDES NUCLEO UNIVERSITARIO RAFAEL RANGEL (NURR) DEPARTAMENTO DE FISICA Y MATEMATICA AREA COMPUTACION TRUJILLO EDO.
UNIVERSIDAD DE LOS ANDES NUCLEO UNIVERSITARIO RAFAEL RANGEL (NURR) DEPARTAMENTO DE FISICA Y MATEMATICA AREA COMPUTACION TRUJILLO EDO. TRUJILLO 1.- Resumen de Prog1 Comentarios es C++ Declaraciones de variables.
Más detallesProgramación Concurrente en Java
Hebras y monitores Departamento de Sistemas Informáticos y Programación Universidad Complutense de Madrid 21 de marzo de 2006 Threads Extendiendo la clase java.lang.thread. public class PrThread extends
Más detallesConcurrencia y paralelismo
Introducción a los Sistemas Operativos Concurrencia y paralelismo 1. Ejecución de programas. Procesos. 2. Multiprogramación Bibliografía Silberschatz and Galvin Sistemas Operativos. Conceptos fundamentales.
Más detallesDiseño Estructurado de Algoritmos
Diseño Estructurado de Algoritmos 1 Sesión No. 11 Nombre: Estructuras algorítmicas. Tercera parte. Objetivo de la sesión: Al concluir la sesión el estudiante aplicará las estructuras algorítmicas repetitivas
Más detallesControl de Flujo. Estructuras de Control! Experiencia Educativa de Algorítmica CONTROL DE FLUJO
Control de Flujo Estructuras de Control Experiencia Educativa de Algorítmica 1 Introducción El estilo de como escribimos y analizamos un algoritmo se convierte en una de las principales características
Más detallesCentro Asociado Palma de Mallorca. Antonio Rivero Cuesta
Centro Asociado Palma de Mallorca Antonio Rivero Cuesta La Sintaxis de Java I... 5 Tipos de datos... 6 Tipos de datos simples... 7 Operadores... 11 Operadores Aritméticos... 12 Operadores relacionales...
Más detallesProgramación en C. Algoritmo y Estructura de Datos. Ing. M. Laura López. Programación en C
Algoritmo y Estructura de Datos Ing. M. Laura López 1 Estructura de un programa en C 2 Estructura de un programa en C #include Archivos de cabecera # define Definición de constantes Declaraciones Globales
Más detallesAplicaciones Concurrentes
PROGRAMACIÓN CONCURRENTE TEMA 6 Aplicaciones Concurrentes ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA DEPARTAMENTO DE CIENCIAS DE LA COMPUTACIÓN PROGRAMACIÓN CONCURRENTE Aplicaciones Concurrentes
Más detallesPara conseguir un correcto funcionamiento de absysnet, es necesario que el programa tenga conocimiento, en la medida de lo posible, de las
Para conseguir un correcto funcionamiento de absysnet, es necesario que el programa tenga conocimiento, en la medida de lo posible, de las particularidades de cada biblioteca, y también las características
Más detallesApuntes de Regulación y Automatización. Prácticas y Problemas.
TEMA 3. AUTOMATISMOS Y AUTÓMATAS PROGRAMABLES. IMPLEMENTACION DE GRAFCET. OBJETIVOS: Los diseños e introducidos en el tema anterior, se traducen de manera sencilla a unas funciones lógicas concretas, esta
Más detallesESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA UNIVERSIDAD DE SEVILLA COMPUTADORAS Y COMUNICACIONES. Redes informáticas de área local (LAN)
ESCUELA TÉCNICA SUPERIOR DE INGENIERÍA INFORMÁTICA UNIVERSIDAD DE SEVILLA COMPUTADORAS Y COMUNICACIONES Práctica 2: Redes informáticas de área local (LAN) 1.Objetivo El objetivo de esta práctica es conseguir
Más detallesTema 7.- Fundamentos de la Programación Orientada a Objetos
Tema 7.- Fundamentos de la Programación Orientada a Objetos 7 de enero de 2014 Objetivos Saber definir clases propias. Saber crear objetos de una clase determinada e interactuar con ellos (Problema 1).
Más detallesConcurrencia: Exclusión mutua y Sincronización
Concurrencia: Exclusión mutua y Sincronización Prof. Carlos Figueira Basado en materiales de Yudith Cardinale (USB) Williams Stallings, Eugene Styer Concurrencia Múltiples aplicaciones Aplicaciones estructuradas
Más detallesCristian Blanco
UNIDAD DIDÁCTICA 8. ANÁLISIS Y DISEÑO ORIENTADO A OBJETOS. DIAGRAMAS DE COMPORTAMIENTO En el siguiente enlace tienes una descripción y algunos ejemplos de todos los diagramas UML.: http://jms32.eresmas.net/tacticos/uml/umlindex.html
Más detallesTEMA 2 Introducción a C# ANÁLISIS Y DESARROLLO DE APLICACIONES INFORMÁTICAS Curso 2010/2011
TEMA 2 Introducción a C# ANÁLISIS Y DESARROLLO DE APLICACIONES INFORMÁTICAS Curso Origen Nuevo lenguaje de propósito general de Microsoft para la plataforma.net Es el único que ha sido diseñado específicamente.net
Más detallesLa Máquina de Acceso Aleatorio (Random Access Machine)
La Máquina de Acceso Aleatorio (Random Access Machine) Nuestro modelo de cómputo secuencial es la máquina de acceso aleatorio (RAM, Random Access Machine) mostrada en la Figura 2.1, y que consiste de:
Más detallesFicha de Aprendizaje N 13
Ficha de Aprendizaje N 13 Curso: Lógica y lenguaje de programación Tema: Fundamentos de programación Duración: 2 horas pedagógicas Logros de aprendizaje Identifica los diferentes tipos de operadores que
Más detalles