Unique & Duplicate List Functions
Here are various subfunctions for manipulating lists in which items appear more than once. The list may be tested for or irradicated of all duplicate items, with a set of functions offering optional tolerances below which items are considered duplicate; or such duplicate items may instead be returned by the function. Alternatively, the number of occurrences of each item in a list may be displayed.
Information about the purpose of each function is detailed in the comments above each function, and the required arguments and returns are demonstrated in the examples.
Contents
Unique
Recursive
Select all
;; Unique - Lee Mac ;; Returns a list with duplicate elements removed. (defun LM:Unique ( l ) (if l (cons (car l) (LM:Unique (vl-remove (car l) (cdr l))))) )
Iterative
Select all
;; Unique - Lee Mac ;; Returns a list with duplicate elements removed. (defun LM:Unique ( l / x r ) (while l (setq x (car l) l (vl-remove x (cdr l)) r (cons x r) ) ) (reverse r) )
Example
(LM:Unique '("A" "B" "B" "B" "C" "C" "D" "E" "E" "E" "E")) => ("A" "B" "C" "D" "E") (LM:Unique '(1 2 3 3 3 4 5 6 6 7 8 8 8 8)) => (1 2 3 4 5 6 7 8)
Unique-p
Recursive
Select all
;; Unique-p - Lee Mac ;; Returns T if the supplied list contains distinct items. (defun LM:Unique-p ( l ) (or (null l) (and (not (member (car l) (cdr l))) (LM:Unique-p (cdr l)) ) ) )
Iterative
Select all
;; Unique-p - Lee Mac ;; Returns T if the supplied list contains distinct items. (defun LM:Unique-p ( l ) (vl-every (function (lambda ( x ) (not (member x (setq l (cdr l)))))) l) )
Example
_$ (LM:Unique-p '(1 2 3 4 5)) T _$ (LM:Unique-p '(1 2 3 3 3 4 5)) nil
Unique with Fuzz
Recursive
Select all
;; Unique with Fuzz - Lee Mac ;; Returns a list with all elements considered duplicate to ;; a given tolerance removed. (defun LM:UniqueFuzz ( l f ) (if l (cons (car l) (LM:UniqueFuzz (vl-remove-if (function (lambda ( x ) (equal x (car l) f))) (cdr l) ) f ) ) ) )
Iterative
Select all
;; Unique with Fuzz - Lee Mac ;; Returns a list with all elements considered duplicate to ;; a given tolerance removed. (defun LM:UniqueFuzz ( l f / x r ) (while l (setq x (car l) l (vl-remove-if (function (lambda ( y ) (equal x y f))) (cdr l)) r (cons x r) ) ) (reverse r) )
Example
_$ (LM:UniqueFuzz '(1.0 1.1 2.0 2.01 2.2) 0.01) (1.0 1.1 2.0 2.2) _$ (LM:UniqueFuzz '(1.0 1.1 2.0 2.01 2.2) 0.15) (1.0 2.0 2.2)
Unique-p with Fuzz
Recursive
Select all
;; Unique-p with Fuzz - Lee Mac ;; Returns T if a list contains items considered distinct to ;; a given tolerance (defun LM:UniqueFuzz-p ( l f ) (or (null l) (and (not (vl-some (function (lambda ( x ) (equal x (car l) f))) (cdr l))) (LM:UniqueFuzz-p (cdr l) f) ) ) )
Iterative
Select all
;; Unique-p with Fuzz - Lee Mac ;; Returns T if a list contains items considered distinct to ;; a given tolerance (defun LM:UniqueFuzz-p ( l f ) (vl-every (function (lambda ( x ) (not (vl-some (function (lambda ( y ) (equal x y f)) ) (setq l (cdr l)) ) ) ) ) l ) )
Example
_$ (LM:UniqueFuzz-p '(1.0 1.1 2.0 2.01 2.2) 0.01) nil _$ (LM:UniqueFuzz-p '(1.0 1.1 2.0 2.01 2.2) 0.001) T
List Duplicates
Recursive
Select all
;; List Duplicates - Lee Mac ;; Returns a list of items appearing more than once in a supplied list (defun LM:ListDupes ( l ) (if l (if (member (car l) (cdr l)) (cons (car l) (LM:ListDupes (vl-remove (car l) (cdr l)))) (LM:ListDupes (vl-remove (car l) (cdr l))) ) ) )
Iterative
Select all
;; List Duplicates - Lee Mac ;; Returns a list of items appearing more than once in a supplied list (defun LM:ListDupes ( l / x r ) (while l (if (member (setq x (car l)) (cdr l)) (setq r (cons x r)) ) (setq l (vl-remove x (cdr l))) ) (reverse r) )
Example
(LM:ListDupes '("A" "B" "B" "B" "C" "C" "D" "E" "E" "E" "E")) => ("B" "C" "E") (LM:ListDupes '(1 2 3 3 3 4 5 6 6 7 8 8 8 8)) => (3 6 8)
Count Items
Recursive
Select all
;; Count Items - Lee Mac ;; Returns a list of dotted pairs detailing the number of ;; occurrences of each item in a supplied list. (defun LM:CountItems ( l / c x ) (if (setq x (car l)) (progn (setq c (length l) l (vl-remove x (cdr l)) ) (cons (cons x (- c (length l))) (LM:CountItems l)) ) ) )
Iterative
Select all
;; Count Items - Lee Mac ;; Returns a list of dotted pairs detailing the number of ;; occurrences of each item in a supplied list. (defun LM:CountItems ( l / c l r x ) (while l (setq x (car l) c (length l) l (vl-remove x (cdr l)) r (cons (cons x (- c (length l))) r) ) ) (reverse r) )
Example
(LM:CountItems '("A" "B" "B" "B" "C" "C" "D" "E" "E" "E" "E")) => (("A" . 1) ("B" . 3) ("C" . 2) ("D" . 1) ("E" . 4)) (LM:CountItems '(1 2 3 3 3 4 5 6 6 7 8 8 8 8)) => ((1 . 1) (2 . 1) (3 . 3) (4 . 1) (5 . 1) (6 . 2) (7 . 1) (8 . 4))