¿Cuándo es útil un ConcurrentSkipListSet?

84

Acabo de ver esta estructura de datos en la API de Java 6 y tengo curiosidad acerca de cuándo sería un recurso útil. Estoy estudiando para el examen scjp y no lo veo cubierto en el libro de Kathy Sierra, aunque he visto preguntas de exámenes simulados que lo mencionan.

andandand
fuente

Respuestas:

175

ConcurrentSkipListSet y ConcurrentSkipListMap son útiles cuando necesitas un contenedor ordenado al que accederán varios subprocesos. Estos son esencialmente los equivalentes de TreeMap y TreeSet para código concurrente.

La implementación de JDK 6 se basa en tablas hash dinámicas sin bloqueo de alto rendimiento y conjuntos basados en listas de Maged Michael en IBM, lo que demuestra que puede implementar muchas operaciones en listas de omisión de forma atómica mediante operaciones de comparación e intercambio (CAS) . Estos no tienen bloqueos, por lo que no tiene que preocuparse por la sobrecarga de synchronized(para la mayoría de las operaciones) cuando usa estas clases.

Actualmente no existe una implementación simultánea de mapas / conjuntos basada en árbol rojo-negro en Java. Revisé un poco la literatura y encontré un par de artículos que mostraban que los árboles RB concurrentes superaban a las listas de omisión, pero muchas de estas pruebas se realizaron con memoria transaccional , que en este momento no es compatible con hardware en ninguna arquitectura importante.

Supongo que los chicos de JDK eligieron una lista de omisión aquí porque la implementación era bien conocida y porque hacerlo sin bloqueos era simple y portátil (usando CAS). Si alguien quiere aclarar, hágalo. Soy curioso.

Todd Gamblin
fuente
1
También es útil si desea realizar un seguimiento de registros únicos en un entorno de subprocesos múltiples de una manera eficiente.
anataliocs
4

Las listas de omisión son listas ordenadas y eficaces para modificar con el rendimiento de log (n). en ese sentido es como TreeSet. sin embargo, no hay ConcurrentTreeSet. Lo que escuché es que la lista de omisión es muy fácil de implementar, probablemente por eso.

De todos modos, cuando necesite un conjunto concurrente, ordenado y eficiente, puede usar ConcurrentSkipListSet

irrefutable
fuente
2

Estos son útiles cuando necesita un conjunto al que varios subprocesos puedan acceder de forma segura simultáneamente. También proporciona un rendimiento decente al ser débilmente consistente: las inserciones se pueden hacer de manera segura mientras itera a través del Conjunto, pero no hay garantía de que su Iterador vea esa inserción.

Kaleb Brasee
fuente
1

ConcurrentSkipListMap fue un hallazgo fantástico cuando necesitaba implementar una capa de replicación para un caché de cosecha propia. Los aspectos del mapa implementaron la caché, y los aspectos subyacentes de la lista me permiten realizar un seguimiento del orden en el que aparecen los objetos en la caché. El aspecto "omitir" de esa lista hizo que fuera eficiente eliminar un objeto de un lugar en la lista y llevarlo al final cuando se reemplazó en la caché.

Patrick Rusk
fuente