2011-03-08 31 views
5

Parece que cuando se programa en Java no se supone que usemos vectores cuando se trata de hilos.¿Qué puedo usar en lugar de un Vector en Java?

¿Qué clase debo usar en lugar de un Vector al usar hilos?

import java.util.Vector; 
Vector<String> v = new Vector<String>(); 

Respuesta

4
List<String> list = Collections.synchronizedList(new ArrayList<String>()); 
+2

Este es un reemplazo de complemento más o menos para 'Vector'. Pero no es necesariamente lo correcto para usar. –

+0

Gracias. Tendré que convertir algunos de mis vectores a listas. – VSH3R

0

matriz, pero si usted no sabe el tamaño, utilice una implementación de concurrentmap

+0

suponiendo que desea un acceso aleatorio rápido a los elementos (razón por la cual la lista sería una mala idea) – necromancer

+0

La diferencia es: un Mapa ofrece acceso aleatorio por clave, una Lista ofrece acceso aleatorio por índice (más o menos eficientemente). –

+0

¿quiere decir que el mapa ofrece O (log (n)) acceso mientras que la Lista ofrece O (1)? luego confunde la discusión para llamarlo una lista: es una matriz enmascarada en una interfaz de lista. si conoce el tamaño, una matriz es claramente la mejor y más fácil de entender. SOLAMENTE si no conoce el tamaño que su elección se encuentra entre un mapa o matrices crecientes que ofrecen un rendimiento algo impredecible en una situación de subprocesos múltiples. – necromancer

-1

utilizar listas y sincronizarlos como

List<?> list = Collections.synchronizedList(new ArrayList<?>()); 
5

Para los casos de rosca insegura, use ArrayList.

Para los casos compatibles con el proceso, utilizar lo que es más apropiado en su caso, CopyOnWriteArrayList, Queue, BlockingDeque, etc. Para un asesoramiento más, necesitamos saber cómo manipular cosas con su colección.

Recomendaría no utilizar el envoltorio Collections.synchronizedList(...) ya que podría no escalarse lo suficiente (a menos que no le importe demasiado la escalabilidad). Pero todo depende de tu contexto.

+0

¿Podría explicar por qué 'Collections.synchronizedList (...)' no se escala? – corsiKa

+1

Si su patrón de uso es 99% de lecturas y 1% de escrituras, CopyOnWriteArrayList proporciona un mejor rendimiento (lea COWAL javadoc). Pero todo depende del patrón de uso. – mindas

+0

Bastante justo - una clase interesante. No estoy 100% seguro de estar de acuerdo (es decir, resuelve un problema que probablemente podría resolverse usando un mejor diseño) pero a veces lo ideal y lo práctico son dos cosas diferentes. +1 – corsiKa

11

Parece que cuando se programa en Java que no se supone que debemos utilizar vectores más cuando se trata de temas.

Es necesario comprender por qué usando Vector se considera que es una mala cosa en la mayoría de los contextos. Las razones son:

  • Vector sincroniza en cada operación. La mayoría de los contextos no requieren una sincronización precisa, y como tal es una sobrecarga de rendimiento no deseada.

  • El método Vector.elements() devuelve Enumeration que no tiene una semántica a prueba de fallos.

Devolviendo esto a su pregunta. Las alternativas dependen de lo que los hilos están tratando de hacer:

  • Si el caso de uso no requiere la sincronización en absoluto, usar ArrayList, o LinkedList. Normalmente los usará si:

    • La lista está restringida por hilos; es decir, solo un hilo puede acceder a él.
    • La lista requiere sincronización de grano grueso; es decir, acceso exclusivo mientras se realiza una secuencia de operaciones. En este caso, normalmente crearía una clase personalizada con un ArrayList incrustado (por ejemplo) que no está expuesto en la API de clases personalizadas.
  • Si el caso de uso requiere la sincronización de grano fino, Collections.synchronizedList envoltura es equivalente a una Vector. Alternativamente, puede quedarse con Vector y evitar el uso de la operación elements().

  • Una lista de CopyOnWriteArrayList tiene la ventaja de que su iterador admite modificaciones simultáneas ... en cierto sentido. También se escala mejor si su aplicación realiza principalmente leer la lista. Las operaciones de lectura no necesitan sincronizarse explícitamente, y generalmente solo necesitan leer un solo volatile una vez. Pero la otra cara de la moneda es que las operaciones de escritura se sincronizan y son significativamente más caras que las ArrayList "normales".

El otro problema con Vector y la Collections.synchronizedList envoltura es que algunos casos de uso requieren sincronización gruesa; p.ej. probar el tamaño de una lista y agregar condicionalmente un elemento en una sola operación sincronizada. Las clases Queue y Deque proporcionan abstracciones de mayor nivel que se ocupan de este tipo de cosas ... para los casos de uso que implican pasar trabajo de forma asincrónica de un hilo a otro.


La conclusión es que no hay una talla única para toda la solución. Debe comprender las características de simultaneidad del diseño de su aplicación y elegir las estructuras de datos correspondientes.


Por último, si se está programando para Java ME, puede ser atrapado con el uso de Vector, dependiendo de lo que J2ME perfil que está apuntando.

+0

@ VSH3R Consulte http://stackoverflow.com/questions/703990/why-is-c-list-not-thread-safe y http://www.ibm. com/developerworks/java/library/j-jtp09263.html. – tiago2014

Cuestiones relacionadas