Enumset.contains

R

Roedy Green

You might think

EnumSet.contains( subset ) would mean containsAnyOf or containsAllOf
but it is meaningless.

There is an EnumSet.containsAll but no EnumSet.containsAnyOf

It seems odd Set and EnumSet don't directly support the usual things
mathematicians do with sets,
union
intersection
isSubsetOf
isSuperSetOf

The operations would be so fast internally if Oracle used the binary
logic ops to handle bit strings, rather than flat-footed processing an
element at a time.

What think you?


--
Roedy Green Canadian Mind Products http://mindprod.com
Ironically, even though the Internet was created by the US military
[DARPA (Defense Advanced Research Projects Agency)]
to withstand a nuclear attack, it is almost defenceless against malice
from any of its users
 
L

Lew

You might think
EnumSet.contains( subset ) would mean containsAnyOf or containsAllOf

Only if you don't read the Javadocs for '[Abstract]Collection#contains()", which make it
pretty obvious that 'contains()' applies to a single instance of the base type.

'EnumSet' is constrained to follow the semantics of the type it overrides with that method.
but it is meaningless.

Nonsense.

It's meaning is clear from the Javadocs. Since an 'EnumSet' has as its base type the enum 'E',
then any call to 'contains(someSubsetNotABaseInstance)' must return 'false'.
There is an EnumSet.containsAll but no EnumSet.containsAnyOf

In this it is just like its parent type.
It seems odd Set and EnumSet don't directly support the usual things

mathematicians do with sets,

union
'addAll()'.
http://docs.oracle.com/javase/7/docs/api/java/util/Set.html#addAll(java.util.Collection)


'retainAll()'
http://docs.oracle.com/javase/7/docs/api/java/util/Set.html#retainAll(java.util.Collection)


uberSet.retainAll(underSet).containsAll(underSet)


'containsAll()'
http://docs.oracle.com/javase/7/docs/api/java/util/Set.html#containsAll(java.util.Collection)

The operations would be so fast internally if Oracle used the binary
logic ops to handle bit strings, rather than flat-footed processing an
element at a time.

What think you?

Three out of four of the operations you wish were directly supported are.

The fourth takes two whole calls to support.
 
R

Robert Klemme

You might think
No.

EnumSet.contains( subset ) would mean containsAnyOf or containsAllOf
but it is meaningless.

There is an EnumSet.containsAll but no EnumSet.containsAnyOf

It seems odd Set and EnumSet don't directly support the usual things
mathematicians do with sets,
union
intersection retainAll()

containsAll()

containsAll()

The operations would be so fast internally if Oracle used the binary
logic ops to handle bit strings, rather than flat-footed processing an
element at a time.

What think you?

You can use clone() and retainAll() and check return type, or use
addAll() and check whether size < oldSize + other.size(), or write a
loop in a few lines...

Cheers

robert
 
A

Andreas Leitgeb

Lew said:
uberSet.retainAll(underSet).containsAll(underSet)

why not just: uberSet.containsAll(underSet) ?

containsAnyOf (for EnumSets es1 and es2):
es1.clone().retainAll(es2).size()>0
it requires actually constructing the intersection,
just to determine if that will be empty or not.

Maybe we're even just lucky, that there is containsAll() in
the Collection framework, or we would have to do it as:
es1.clone().retainAll(es2).size() == es2.size()
 
R

Roedy Green

retainAll()

These are methods of AbstractSet inherited and in my opinion
preposterously pedestrian. You might as well have used a TreeSet as an
Enum. A proper intersection method for EnumSets would be implemented
with a single AND machine instruction.

Mathematicians have been using the term "intersection" for at least
100 years. I think it was improper of Sun/Oracle to rename the
functions.

--
Roedy Green Canadian Mind Products http://mindprod.com
Ironically, even though the Internet was created by the US military
[DARPA (Defense Advanced Research Projects Agency)]
to withstand a nuclear attack, it is almost defenceless against malice
from any of its users
 
M

markspace

A proper intersection method for EnumSets would be implemented
with a single AND machine instruction.


Have you checked the source code, Roedy?

Mathematicians have been using the term "intersection" for at least
100 years. I think it was improper of Sun/Oracle to rename the
functions.


Maybe. Maybe Sun was just checking who could read the docs.
 
J

Joshua Cranmer

These are methods of AbstractSet inherited and in my opinion
preposterously pedestrian. You might as well have used a TreeSet as an
Enum. A proper intersection method for EnumSets would be implemented
with a single AND machine instruction.

The implementations aren't actually inherited from AbstractSet. If you
pay careful attention to the documentation, you'll notice that EnumSet
is an abstract class. The actual implementation is one of two classes,
RegularEnumSet or JumboEnumSet, which is selected based on the number of
elements in the enum. In these subclasses, the methods are indeed
overridden for increased performance.

From the source code of java.util.RegularEnumSet (the actual
implementation of EnumSets for enums with <= 64 characters):
public boolean retainAll(Collection<?> c) {
if (!(c instanceof RegularEnumSet))
return super.retainAll(c);

RegularEnumSet<?> es = (RegularEnumSet<?>)c;
if (es.elementType != elementType) {
boolean changed = (elements != 0);
elements = 0;
return changed;
}

long oldElements = elements;
elements &= es.elements;
return elements != oldElements;
}

Up to the necessary boilerplate, it is exactly an AND machine instruction.
Mathematicians have been using the term "intersection" for at least
100 years. I think it was improper of Sun/Oracle to rename the
functions.

Except that java.util.Set isn't a set in the mathematical sense, but a
specification of an abstract datatype called a "set" (a collection of
items such that no item is contained more than once). There is a
distinction between the two; in particular, a mathematical set is an
intrinsically immutable object while the set datatype is definitely mutable.

Case in point: what would a.intersection(b) do?
1. Return a set c which consists of all elements that are both in a and
b at the point of the function call.
2. Return a set c which gives you a view of the elements that are both
in a and b at the time of any given function call in c (so if you remove
an element from a, it may be removed from c as well).
3. Update a to consist only of the elements that it shares in common with b.

You can make arguments for doing any of these three things (and perhaps
choose a better name than a noun for a method call). On the other hand,
retainAll tells you exactly which of the three it will do.

To paraphrase one of my programming books, relationships in
object-oriented programming don't necessarily follow the same
relationships in mathematics, even if they have the same name.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,763
Messages
2,569,563
Members
45,039
Latest member
CasimiraVa

Latest Threads

Top