8

Consider this example:

Complement[{a, y, c, d, e}, {a, c}, {d}]
(*{e, y}*)

However, I was expecting the result to be:

(*{y,e}*)

Why did Complement[] reorder the resulting list?

Any idea how to get the desired results (list with elements in their original order), using Complement[]?

J. M.'s missing motivation
  • 124,525
  • 11
  • 401
  • 574
Basheer Algohi
  • 19,917
  • 1
  • 31
  • 78

5 Answers5

8

It uses sorting internally (as documented, actually). For unsorted, could do as below.

unsortedComplement[l1_, l2_] := Reap[Module[
    {remove},
    Map[(remove[#] = True) &, l2];
    Map[If[TrueQ[remove[#]], Null, Sow[#]] &, l1];
    Clear[remove];
    ]][[2, 1]]

unsortedComplement[{1, 3, 2, 8, 5}, {3, 6}]

(* Out[78]= {1, 2, 8, 5} *)

Extending to more lists is straightforward.enter code here

Daniel Lichtblau
  • 58,970
  • 2
  • 101
  • 199
  • Thanks. there are so many other ways to get the desired results. I was just wondering if there is any way to tell Complement to unsort the result. perhaps I should have read the document carefully. thanks for the answer – Basheer Algohi Sep 10 '14 at 20:08
7

This should get you the desired result:

 Select[{a, y, c, d, e}, MemberQ[Union[{a, c}, {d}], #] == False &]

{y, e}

paw
  • 5,650
  • 23
  • 31
6

If you want to stick with Complement[]

l = {a, y, c, d, e};;
l[[Sort[Complement[l, {a, c}, {d}] /. Thread[l -> Range@Length@l]]]]
(*{y, e}*)

or

SortBy[Complement[l, {a, c}, {d}], Position[l, #] &]
(*{y, e}*)
Dr. belisarius
  • 115,881
  • 13
  • 203
  • 453
2
la = {a, y, c, d, e};
lb = {a, c};
lc = {d};

Since V 13.1 we have DeleteElements and UniqueElements

DeleteElements[la, Join[lb, lc]]

{y, e}

UniqueElements[{la, lb, lc}]

{{y, e}, {}, {}}

First[%]

{y, e}

eldo
  • 67,911
  • 5
  • 60
  • 168
2

Using DeleteCases:

DeleteCases[{a, y, c, d, e}, Alternatives @@ Union @@ {{a, c}, {d}}]

({y, e})

E. Chan-López
  • 23,117
  • 3
  • 21
  • 44