1

Mathematica allows Deleting multiple objects from a list given their position. However, if I don't know their positions (finding their positions in the list is too costly if the list is long), how can I directly delete multiple objects from a List in an efficient manner (based on their value)?

J. M.'s missing motivation
  • 124,525
  • 11
  • 401
  • 574
Iconoclast
  • 503
  • 2
  • 9

1 Answers1

2

You can map the deleted values to Nothing with a Dispatch rule list.

someList = RandomInteger[{1, 5000}, 50000];
someDelList = RandomInteger[{1, 500}, 500];
someDelRules = Dispatch[Map[# -> Nothing &, someDelList]];

It can compare favorably timing wise with the naive overhead of sweeping through to find positions, then dropping those positions with Delete.

RepeatedTiming[someNewList1 = someList /. someDelRules;]

yields

{0.012, Null}

RepeatedTiming[
 someNewList2 = 
   Delete[someList, 
    Flatten[Position[someList, #] & /@ someDelList, 1]];]

yields

{1.72, Null}

With someNewList2 === someNewList1 $\mapsto$ True and Length[someNewList]$\mapsto$ 46862 .

Can also compare with a naive DeleteCases:

RepeatedTiming[
  someNewList3 = 
   DeleteCases[someList, (x_ /; !FreeQ[someDelList, x])];]

yielding:

{0.815, Null}

With also someNewList3 === someNewList1$\mapsto$True.

Update

Alternatives is the magic for DeleteCases.

  RepeatedTiming[
     someNewList4 = 
     DeleteCases[someList, Alternatives[someList]];]

yields

(.0053, Null)

Documentation here.