Mathematica Asked by PeriodicProgrammer on March 13, 2021
I’m new to functional programming of Mathematica and trying to remove one list of assorted elements from another. However I only find functions working with the Index rather than the values itself:
list1={b,a,e,f,c,d}
list2={f,e,c}
I can now remove list2
from list1
:
result={b,a,d}
I already found out, that you can “abuse”
DeleteCases[list1, a]
to remove 1 specific element from a list, but not a whole assorted list…
I would be very grateful for a simple solution to do it.
Thanks a lot for any answer!
Use
DeleteCases[list1, Alternatives @@ list2]
In new versions (M8.0+), DeleteCases
is optimized on patterns not involving blanks, so this will be fast also for large lists. For earlier versions, this will work:
Replace[list1, Dispatch[Thread[list2 -> Sequence[]]],{1}]
being 2-3 times slower, but still very fast.
Correct answer by Leonid Shifrin on March 13, 2021
You are perhaps searching for Complement
. Complement[list1, list2]
results in {a, b, d}
. The result is sorted though. If you are looking for an unsorted complement, DeleteCases[list1, Alternatives @@ list2]
should probably work. I think there are some discussions on unsorted complements out there at google.
Answered by Yves Klett on March 13, 2021
Since Yves beat me narrowly to my first solution, here's another one using Select
:
Select[list1, FreeQ[list2, #] &]
Out[2]= {b, a, d}
This does not sort your result.
You can also use Complement
, which is more intuitive. Example:
Complement[list1, list2]
Out[1]= {a, b, d}
Note that this sorts your result (i.e., it is not in the same order, {b, a, d}
).
Answered by rm -rf on March 13, 2021
Iff each list is internally free of duplicates you can use this very quick method:
DeleteDuplicates[#2 ~Join~ #] ~Drop~ Length[#2] &[list1, list2]
Answered by Mr.Wizard on March 13, 2021
Unsorted Complement
. I think it originates from MathGroup. It accepts the SameTest
option.
Options[UnsortedComplement] = {SameTest -> Automatic};
UnsortedComplement[all_, del___, opts : OptionsPattern[]] :=
Replace[all,
List @@ (Rule[#, Sequence[]] & /@ Union[del, opts]), {1}];
all = RandomInteger[{0, 9}, {20}]
UnsortedComplement[all, {6, 2, 8}, {2, 3, 4}]
(*
==> {8, 4, 2, 5, 8, 8, 6, 6, 2, 1, 3, 1, 1, 2, 8, 0, 5, 5, 8, 1}
==> {5, 1, 1, 1, 0, 5, 5, 1}
*)
It also works with any head, not just List
-s.
Answered by István Zachar on March 13, 2021
Just nest it:
Fold[DeleteCases[#1, #2] &, list1, list2]
Answered by Fortsaint on March 13, 2021
I hesitate to add to this old discussion after these excellent answers and other essential reading especially here, but this amalgamation of many suggestions may be of interest. cutEverything[xx_, removeList__] removes all entries of all elements of removeList_ from xx_ regardless of their depth or whether they are duplicates. It leaves compounds in place and does not change the original list order.
x =
{pudepied, pudepied.txt, {pudepied}, {{{pudepied}}, {zap}, {{peter}}}, {{pudepied}},
blah, zap, "Wolfram Language", {peter}, {{{}}}, mary, {{{{mary}}}}};
remove = {pudepied, peter, mary, {}};
cutEverything[xx_, removeList_] :=
Replace[xx, x_List :> DeleteCases[x, Alternatives @@ removeList], {0, Infinity}]
cutEverything[x, remove]
{pudepied.txt, {{zap}}, blah, zap, Wolfram Language}
Answered by pudepied on March 13, 2021
Get help from others!
Recent Answers
Recent Questions
© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP