¿Existe .asSet (…) en alguna API?

Respuestas:

84

Ahora con Java 8 puedes hacer esto sin necesidad de un marco de terceros:

Set<String> set = Stream.of("a","b","c").collect(Collectors.toSet());

Ver coleccionistas .

¡Disfrutar!

Sr. Anderson
fuente
4
Hoy en día, con Java 8, esta es probablemente la mejor respuesta porque no depende de bibliotecas de terceros y se puede adaptar fácilmente a otros tipos de colecciones, por lo que estoy configurando esto como el aceptado. Muchas gracias a todos por las otras excelentes soluciones. (por cierto, este set es mutable)
cahen
3
Ahora, ¿quién dijo que Java era demasiado detallado? ¡Por supuesto que esta es la mejor respuesta!
BobDoolittle
¡Muchas gracias @BobDoolittle!
Sr. Anderson
2
Para cualquier persona que use java 9+, consulte también la respuesta de Holly a continuación: stackoverflow.com/a/48025159/229743
Taylor
1
respuesta impecable Sr. Anderson!
gaurav
63

Usando Guava , es tan simple como eso:

Set<String> mySet = ImmutableSet.<String> of("a", "b");

O para un conjunto mutable:

Set<String> mySet = Sets.newHashSet("a", "b")

Para obtener más tipos de datos, consulte la guía del usuario de Guava

Michael Schmeißer
fuente
¿Existe una versión no inmutable de esto?
Cahen
3
@cahen sí: Sets.newHashSet("a", "b")oSets.newLinkedHashSet("a", "b")
Sean Patrick Floyd
1
Agregué una variante mutable a la respuesta.
Michael Schmeißer
en realidad, Sets.newLinkedHashSet()no existe con esa firma, lo siento
Sean Patrick Floyd
Pude eliminar uno de los argumentos de tipo:Set<String> mySet = ImmutableSet.of("a", "b");
joshden
54

Podrías usar

new HashSet<String>(Arrays.asList("a","b"));
Dev en blanco
fuente
24

Para los casos especiales de conjuntos con cero o un miembro, puede utilizar:

java.util.Collections.EMPTY_SET

y:

java.util.Collections.singleton("A")
Samuel Edwin Ward
fuente
para estos casos especiales, es probable que sea la mejor solución, ya que utiliza la API estándar java.util
arcuri82
2
java.util.Collections.emptySet()es, en mi opinión, preferido sobre EMPTY_SET, debido a la seguridad de tipos. De los comentarios en la clase Colecciones:Unlike the like-named field, this method is parameterized.
Edificado el
17

Como han dicho otros, use:

new HashSet<String>(Arrays.asList("a","b"));

La razón por la que esto no existe en Java es que Arrays.asListdevuelve una lista de tamaño fijo, en otras palabras:

public static void main(String a[])
{
  List<String> myList = Arrays.asList("a", "b");
  myList.add("c");
}

Devoluciones:

Exception in thread "main" java.lang.UnsupportedOperationException
    at java.util.AbstractList.add(Unknown Source)
    at java.util.AbstractList.add(Unknown Source)

No existe una implementación JDK de un "tamaño fijo" Setdentro de la Arraysclase. ¿Por qué quieres esto? A Setgarantiza que no hay duplicados, pero si los está escribiendo a mano, no debería necesitar esa funcionalidad ... y Listtiene más métodos. Ambas interfaces amplían Collectiony Iterable.


Como han dicho otros, use guava si realmente desea esta funcionalidad, ya que no está en el JDK. Mire sus respuestas (en particular la respuesta de Michael Schmeißer) para obtener información al respecto.

durron597
fuente
3
Esta es la mejor respuesta hasta ahora, porque señala lo que realmente hace Arrays.asList (). Muchos desarrolladores parecen creer que Arrays.asList () crea un java.util.ArrayList, mientras que en realidad crea un java.util.Arrays $ ArrayList (que es solo parcialmente mutable y una vista en vivo de la matriz subyacente)
Sean Patrick Floyd
1
En cuanto a por qué alguien querría hacer esto, la razón más común para construir un Conjunto (o Lista) a mano es en una clase de prueba donde está pasando valores de prueba.
Scott McIntyre
14

En Java 9, se ha agregado una función similar a través de métodos de fábrica:

Set<String> oneLinerSet = Set.of("a", "b", ...);

(También hay equivalentes para List).

Acebo cummins
fuente
Intenté esto y recibí una advertencia del compilador de que este no es un método API.
Philippe Gioseffi
Aquí está el documento de Java relevante: docs.oracle.com/javase/9/docs/api/java/util/Set.html . Además de usar un JDK de Java 9+, es posible que deba ajustar su IDE o herramienta de compilación para usar el cumplimiento de Java 9 (por ejemplo, para maven, serían pasos similares a los de aquí, pero establecidos en 1.9: stackoverflow.com/ preguntas / 16798066 /… )
Holly Cummins
Ojalá pudiéramos usar Java 9. ¡Estamos viviendo en el pasado! :(
jDub9
eso es bueno pero tiene algunas restricciones en el tamaño de los argumentos ...
Radoslav Ivanov
3

No, pero puedes hacerlo así

new HashSet<String>(Arrays.asList("a", "b", ...));
Evgeniy Dorofeev
fuente
2

Aquí tienes un pequeño método que puedes usar

  /**
   * Utility method analogous to {@link java.util.Arrays#asList(Object[])}
   *
   * @param ts
   * @param <T>
   * @return the set of all the parameters given.
   */
  @SafeVarargs
  @SuppressWarnings("varargs")
  public static <T> Set<T> asSet(T... ts) {
    return new HashSet<>(Arrays.asList(ts));
  }
Stuart Clark
fuente
1

Otra forma de hacerlo usando Java 8 y enumeraciones sería:

Set<String> set = EnumSet.of(StandardOpenOption.CREATE, StandardOpenOption.READ);

Ver EnumSet .

Recomendaría un análisis de desempeño entre este enfoque y

Set<String> set = Stream.of(StandardOpenOption.CREATE, StandardOpenOption.READ).collect(Collectors.toSet());

porque si tienes más de cinco elementos, el javadoc del método indica que pueden ser problemas de rendimiento como puedes ver en el javadoc de Set.Of (E, E ...) .

Philippe Gioseffi
fuente