¿Por qué no la eliminación de un TreeSet con un comparador de encargo eliminar un grupo mayor de elementos?

Nikolas:

El uso de ambos Java 8 y Java 11, considere lo siguiente TreeSetcon un String::compareToIgnoreCasecomparador:

final Set<String> languages = new TreeSet<>(String::compareToIgnoreCase);
languages.add("java");
languages.add("c++");
languages.add("python");

System.out.println(languages);                 // [c++, java, python]

Cuando intento para eliminar los elementos exactos presente en el TreeSet, funciona: todos los especificados se eliminan:

languages.removeAll(Arrays.asList("PYTHON", "C++"));

System.out.println(languages);                 // [java]

Sin embargo, si intento para eliminar vez más que está presente en el TreeSet, la llamada no quita nada en absoluto (esto no es una llamada posterior, pero llama en lugar del fragmento anterior):

languages.removeAll(Arrays.asList("PYTHON", "C++", "LISP"));

System.out.println(languages);                 // [c++, java, python]

¿Qué estoy haciendo mal? ¿Por qué se comportan de esta manera?

Editar: String::compareToIgnoreCasees un comparador válida:

(l, r) -> l.compareToIgnoreCase(r)
JB Nizet:

Aquí está el javadoc de removeAll () :

Esta implementación determina que es el más pequeño de este conjunto y la colección especificada, invocando el método tamaño en cada uno. Si este conjunto tiene menos elementos, entonces se repite el de la aplicación durante este conjunto, comprobando cada elemento devuelto por el iterador a su vez para ver si está contenida en la colección especificada. Si así se contenía, se elimina de este conjunto con método remove del iterador. Si la colección especificada tiene menos elementos, entonces los itera de ejecución más de la colección especificada, eliminando de este conjunto cada elemento devuelto por el iterador, utilizando método remove de este conjunto.

En el segundo experimento, que está en el primer caso del javadoc. Por lo que itera sobre "java", "C ++", etc., y comprueba si están contenidos en el conjunto devuelto por Set.of("PYTHON", "C++"). No son, por lo que no están eliminados. Utilice otro TreeSet utilizando el mismo argumento como comparador, y debería funcionar bien. El uso de dos implementaciones diferentes Set, uno usando equals(), y la otra utilizando un comparador, es una cosa peligrosa de hacer efectivamente.

Tenga en cuenta que hay un error abierto acerca de esto: [JDK-8180409] TreeSet removeAll comportamiento incoherente con String.CASE_INSENSITIVE_ORDER .

Supongo que te gusta

Origin http://10.200.1.11:23101/article/api/json?id=427301&siteId=1
Recomendado
Clasificación