4
$\begingroup$

I have two intervals:

i1 = Interval[{1,4}];
i2 = Interval[{2,3}];

I need a function that subtracts i2 from i1, returning:

Interval[{1,2},{3,4}]

In other words, is there an analog of the Complement function for intervals? And if not, how would one implement it?

$\endgroup$
5
  • 4
    $\begingroup$ On the right side of this page, you'll see a list of related questions. One of the related questions is about finding complements of intervals:? mathematica.stackexchange.com/questions/11345/… $\endgroup$
    – Searke
    Mar 30, 2016 at 2:28
  • $\begingroup$ Please note that Interval objects represent closed intervals. If you complement two such overlapping intervals, the result will have an interval with an open end. You can't represent that on Mathematica with a plain Interval object. $\endgroup$
    – kirma
    Mar 30, 2016 at 4:17
  • 2
    $\begingroup$ @Searke, I've seen that answer, but it does not seem to be very scalable. I have thousands of intervals, and it would be hard to redefine all of them as inequalities. $\endgroup$
    – verse
    Mar 30, 2016 at 5:35
  • $\begingroup$ @kirma, In my particular application it doesn't matter whether the intervals or open or closed, if there's a way to represent the resulting set as a closed interval (even if strictly speaking it should be open), I'd love to know it. $\endgroup$
    – verse
    Mar 30, 2016 at 5:35
  • $\begingroup$ Have you seen Are there Min and Max functions that work properly on Intervals? $\endgroup$
    – user9660
    Mar 30, 2016 at 9:56

2 Answers 2

6
$\begingroup$

If you do not bother about the endpoints, you could define a complement function in the following way:

complement[x_Interval] := Interval @@ Partition[Flatten[{-\[Infinity], List @@ x, \[Infinity]}], 2]


complement[Interval[{1,2}]]
(* Interval[{-\[Infinity],1},{2,\[Infinity]}]*)

complement[Interval[{1,2},{3,4}]]
(*Interval[{-\[Infinity],1},{2,3},{4,\[Infinity]}]*)

Subtracting can be done with IntervalIntersection:

a=Interval[{0, 10}];
b=Interval[{1,3}, {7, 12}];
IntervalIntersection[a, complement[b]]

(*Interval[{0,1},{3,7}]*)
$\endgroup$
1
  • $\begingroup$ Fred, this is great. Thanks so much! $\endgroup$
    – verse
    Mar 30, 2016 at 16:34
2
$\begingroup$
ClearAll[itrF, slitrF, intervalComplementF]
slitrF = Statistics`Library`IntervalToRegion;
itrF[x_][Interval[p : {_, _} ..]] := Or @@ (slitrF[#, x] & /@ Interval /@ {p});
intervalComplementF = Interval @@ (Reduce[itrF[x]@# && Not[itrF[x]@#2], x, Reals] /. 
  { Or -> List , Inequality[a_, __, b_] :> {a, b}, 
  Less[_, a_] | LessEqual[_, a_] :> {-Infinity, a}, 
  Greater[_, b_] | GreaterEqual[_, b_] :> {b, Infinity}} ) &;

Examples:

i1 = Interval[{1, 4}];
i2 = Interval[{2, 3}]; 
intervalComplementF[i1, i2]

Interval[{1, 2}, {3, 4}]

a = Interval[{0, 10}];
b = Interval[{1, 3}, {7, 12}];
intervalComplementF[a, b]

Interval[{0, 1}, {3, 7}]

intervalComplementF[Interval[{-Infinity, Infinity}], Interval[{2, 3}, {5, 6}]]

Interval[{-Infinity, 2}, {3, 5}, {6, Infinity}]

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.