Bilal Qadri
Bilal Qadri

Reputation: 141

More than one argument for predicate in delete-if

Suppose I want to delete one step (element) from the states list.

(defparameter *states* '((:top nil nil) (:subjects nil nil)))
 ;predicate
(defun equal-state? (step state)
  (equal (car step) state))

If I use (delete-if #'equal-state? *states*) then how the second argument ( state) can be passed to predicate?

edited: I have finally found a similar question but I am inclined to retain it because of clarity in the question.

Upvotes: 0

Views: 108

Answers (1)

Rainer Joswig
Rainer Joswig

Reputation: 139251

CL-USER 67 > (let ((state :top))
               (delete-if (lambda (step)
                            (equal-state? step state))
                          *states*))
((:SUBJECTS NIL NIL))

or

CL-USER 68 > (defun make-predicate (state)
               (lambda (step)
                 (equal-state? step state)))
MAKE-PREDICATE

CL-USER 69 > (delete-if (make-predicate :subjects)
                        *states*)
((:TOP NIL NIL))

As user coredump mentions, delete-if is a potentially destructive operation. The non-destructive alternative to delete-if is remove-if.

One can also use remove/ delete:

CL-USER 77 > (remove :subjects
                     '((:top nil nil)
                       (:subjects nil nil))
                     :key #'first
                     :test #'equal)
((:TOP NIL NIL))

Upvotes: 3

Related Questions