@@ -59,17 +59,20 @@ def get_set(self):
5959class OpBuilderInputType (Enum ):
6060 SET = 1
6161 STREAM_BUILDER = 2
62+ UNION = 3
6263
6364
6465class OpBuilder (object ):
6566
6667 _BUILDERS = {
6768 OpBuilderInputType .SET : lib .fst_set_make_opbuilder ,
6869 OpBuilderInputType .STREAM_BUILDER : lib .fst_set_make_opbuilder_streambuilder ,
70+ OpBuilderInputType .UNION : lib .fst_set_make_opbuilder_union ,
6971 }
7072 _PUSHERS = {
7173 OpBuilderInputType .SET : lib .fst_set_opbuilder_push ,
7274 OpBuilderInputType .STREAM_BUILDER : lib .fst_set_opbuilder_push_streambuilder ,
75+ OpBuilderInputType .UNION : lib .fst_set_opbuilder_push_union ,
7376 }
7477
7578 @classmethod
@@ -452,3 +455,66 @@ def __iter__(self):
452455 for fst in self .sets [1 :]:
453456 opbuilder .push (fst ._ptr )
454457 return opbuilder .union ()
458+
459+ def _make_opbuilder (self , * others ):
460+ others = list (others )
461+ if len (self .sets ) <= 1 :
462+ raise ValueError (
463+ "Must have more than one set to operate on." )
464+ if not others :
465+ raise ValueError (
466+ "Must have at least one set to compare against." )
467+ our_opbuilder = OpBuilder (self .sets [0 ]._ptr ,
468+ input_type = OpBuilderInputType .SET )
469+ for fst in self .sets [1 :]:
470+ our_opbuilder .push (fst ._ptr )
471+ our_stream = lib .fst_set_opbuilder_union (our_opbuilder ._ptr )
472+
473+ their_opbuilder = OpBuilder (others .pop ()._ptr ,
474+ input_type = OpBuilderInputType .SET )
475+ for fst in others :
476+ their_opbuilder .push (fst ._ptr )
477+ their_stream = lib .fst_set_opbuilder_union (their_opbuilder ._ptr )
478+
479+ opbuilder = OpBuilder (our_stream , input_type = OpBuilderInputType .UNION )
480+ opbuilder .push (their_stream )
481+ return opbuilder
482+
483+ def difference (self , * others ):
484+ """ Get an iterator over the keys in the difference of this set and
485+ others.
486+
487+ :param others: List of :py:class:`Set` objects
488+ :returns: Iterator over all keys that exists in this set, but in
489+ none of the other sets, in lexicographical order
490+ """
491+ return self ._make_opbuilder (* others ).difference ()
492+
493+ def intersection (self , * others ):
494+ """ Get an iterator over the keys in the intersection of this set and
495+ others.
496+
497+ :param others: List of :py:class:`Set` objects
498+ :returns: Iterator over all keys that exists in all of the passed
499+ sets in lexicographical order
500+ """
501+ return self ._make_opbuilder (* others ).intersection ()
502+
503+ def symmetric_difference (self , * others ):
504+ """ Get an iterator over the keys in the symmetric difference of this
505+ set and others.
506+
507+ :param others: List of :py:class:`Set` objects
508+ :returns: Iterator over all keys that exists in only one of the
509+ sets in lexicographical order
510+ """
511+ return self ._make_opbuilder (* others ).symmetric_difference ()
512+
513+ def union (self , * others ):
514+ """ Get an iterator over the keys in the union of this set and others.
515+
516+ :param others: List of :py:class:`Set` objects
517+ :returns: Iterator over all keys in all sets in lexicographical
518+ order
519+ """
520+ return self ._make_opbuilder (* others ).union ()
0 commit comments