sadhu Posted June 25, 2010 Posted June 25, 2010 I'm looking for a lisp to test if an element is repeated in a list and how many times. e.g. (A B C D A 1 2 12 2 XX) A = 2 2 = 2 I've written this but ... (setq kcnt 0) (while ( (setq mcnt (+ 1 kcnt)) (while ( (if (= (nth kcnt fdp_BLK_NUM_LST) (nth mcnt fdp_BLK_NUM_LST)) (progn (prc (strcat " La scatola # " (nth kcnt fdp_BLK_NUM_LST) " si ripete nel foglio di produzione")) (setq fdp_errore_scatola 1) ));if (setq mcnt (+ 1 mcnt)) );while (setq kcnt (+ kcnt 1)) );while (if (= fdp_errore_scatola 0)(prc " -- OK --")) Thanks. Quote
MSasu Posted June 25, 2010 Posted June 25, 2010 Maybe the code below will help you: (setq ItemCounter 0) ;occurrencies counter set to 0 (while (member theItem theList) ;test if item belong to list (setq theList (cdr (member theItem theList)) ;if found retain list after occurrence ItemCounter (1+ ItemCounter)) ; and index the counter ) Regards, Quote
alanjt Posted June 25, 2010 Posted June 25, 2010 I wrote this a while back... (defun AT:ListDuplicates (lst) ;; Return all duplicates within list ;; lst - List to process ;; Alan J. Thompson, 11.01.09 (vl-remove-if-not (function (lambda (x) (member x (cdr (member x lst))))) lst) ) eg. (at:listduplicates '(1 2 3 4 5 1 2 3)) -> [color=Red](1 2 3 1 2 3)[/color] Quote
fixo Posted June 25, 2010 Posted June 25, 2010 I'm looking for a lisp to test if an element is repeated in a list and how many times. e.g. (A B C D A 1 2 12 2 XX) A = 2 2 = 2 I've written this but ... Thanks. Here is my 2 cents (defun count_occurs (lst) (if (car lst) (cons (cons (car lst) (length (vl-remove-if-not (function (lambda (x) (eq x (car lst)))) lst)) ) (count_occurs (vl-remove-if (function (lambda (x) (eq x (car lst)))) lst) ) ) ) ) ~'J'~ Quote
alanjt Posted June 25, 2010 Posted June 25, 2010 I misunderstood the desired result... (defun _ListDuplicateCount (lst / c new) ;; Alan J. Thompson, 06.25.10 (foreach x (vl-remove-if-not (function (lambda (x) (member x (cdr (member x lst))))) lst) (if (setq c (assoc x new)) (setq new (subst (cons x (+ (cdr c) 1)) c new)) (setq new (append new (list (cons x 1)))) ) ) ) Quote
sadhu Posted June 25, 2010 Author Posted June 25, 2010 Thanks fixo Thanks Alan Thanks masau You guys are of great help. Quote
VVA Posted June 25, 2010 Posted June 25, 2010 A little late, but will add my 5 cents (defun mip_MakeUniqueMembersOfListWithCount ( lst / OutList head countelt) ;; ===== mip_MakeUniqueMembersOfListWithCount ===== ;; Removes the same (duplicate) items from the list ;; Quantifying the number of occurrences of an element ;; Use: ;; (Mip_MakeUniqueMembersOfListWithCount '(1 2 3 1 2 3 1 1 2 2)) ;; Return ((1. 4) (2. 4) (3. 2)) (while lst (setq head (car lst) countelt 0 lst (vl-remove-if '(lambda(pt)(if (equal pt head 1e-6)(setq countelt (1+ countelt)) nil)) lst) OutList (append OutList (list (cons head countelt))))) OutList ) Quote
alanjt Posted June 26, 2010 Posted June 26, 2010 (defun _ListDuplicateCounter (lst / c new) ;; Alan J. Thompson, 06.26.10 (foreach x lst (if (setq c (assoc x new)) (setq new (subst (cons x (1+ (cdr c))) c new)) (setq new (append new (list (cons x 1)))) ) ) ) Quote
sadhu Posted July 7, 2010 Author Posted July 7, 2010 Hi Alan, I using this code (defun _ListDuplicateCounter (lst / c new) ;; Alan J. Thompson, 06.26.10 (foreach x lst (if (setq c (assoc x new)) (setq new (subst (cons x (1+ (cdr c))) c new)) (setq new (append new (list (cons x 1)))) ) ) ) like this (defun c:repeat_test() (setq my_lst (list 1 2 3 4 5 6 6 1 1 2 2 3 3)) (setq my_new_lst ( _ListDuplicateCounter my_lst)) (princ my_new_lst)(princ) ) and i get this fantastic result ((1 . 3) (2 . 3) (3 . 3) (4 . 1) (5 . 1) (6 . 2)) I need to distinguish items that repeat odd number of times (actually elements that repeat once, thrice and 5 times would suffice). A result with the command "prc" - i print to a text file "1" repeats 3 "2" repeats 3 "3" repeats 3 "4" repeats 1 "5" repeats 1 6 excluded and not printed. thanks:roll: Quote
Lee Mac Posted July 7, 2010 Posted July 7, 2010 Slightly late to the party, but my 2 cents: (defun LM:ListDupes ( lst ) ;; © Lee Mac 2010 (if lst (if (vl-position (car lst) (cdr lst)) (cons (cons (car lst) (- (length lst) (length (vl-remove (car lst) lst))) ) (LM:ListDupes (vl-remove (car lst) lst)) ) (LM:ListDupes (cdr lst)) ) ) ) Quote
alanjt Posted July 7, 2010 Posted July 7, 2010 (vl-remove-if-not (function (lambda (x) (vl-position (car x) '(1 3 5)))) (_ListDuplicateCounter my_lst) ) Hi Alan, I using this code (defun _ListDuplicateCounter (lst / c new) ;; Alan J. Thompson, 06.26.10 (foreach x lst (if (setq c (assoc x new)) (setq new (subst (cons x (1+ (cdr c))) c new)) (setq new (append new (list (cons x 1)))) ) ) ) like this (defun c:repeat_test() (setq my_lst (list 1 2 3 4 5 6 6 1 1 2 2 3 3)) (setq my_new_lst ( _ListDuplicateCounter my_lst)) (princ my_new_lst)(princ) ) and i get this fantastic result ((1 . 3) (2 . 3) (3 . 3) (4 . 1) (5 . 1) (6 . 2)) I need to distinguish items that repeat odd number of times (actually elements that repeat once, thrice and 5 times would suffice). A result with the command "prc" - i print to a text file "1" repeats 3 "2" repeats 3 "3" repeats 3 "4" repeats 1 "5" repeats 1 6 excluded and not printed. thanks:roll: Quote
Lee Mac Posted July 7, 2010 Posted July 7, 2010 I need to distinguish items that repeat odd number of times (defun LM:ListDupes ( lst ) ;; © Lee Mac 2010 (if lst (if (vl-position (car lst) (cdr lst)) (cons (cons (car lst) (- (length lst) (length (vl-remove (car lst) lst))) ) (LM:ListDupes (vl-remove (car lst) lst)) ) (LM:ListDupes (cdr lst)) ) ) ) (defun LM:GetOddDupes ( lst ) ;; © Lee Mac 2010 (vl-remove-if-not '(lambda ( x ) (= 1 (boole 1 1 (cdr x)))) (LM:ListDupes lst) ) ) Quote
sadhu Posted July 7, 2010 Author Posted July 7, 2010 Alan, I made this modification and does my case. (vl-remove-if-not (function (lambda (x) (vl-position ([b][color=Red]cdr [/color][/b]x) '(1 3 5)))) (_ListDuplicateCounter my_lst) Thanks a million. Quote
sadhu Posted July 7, 2010 Author Posted July 7, 2010 Lee, I tried your code like this - I get result nil - am I missing something ? (defun c:repeat_test() (setq my_lst (list 1 2 3 4 4 5)) (defun LM:ListDupes ( lst ) ;; © Lee Mac 2010 (if lst (if (vl-position (car lst) (cdr lst)) (cons (cons (car lst) (- (length lst) (length (vl-remove (car lst) lst))) ) (LM:ListDupes (vl-remove (car lst) lst)) ) (LM:ListDupes (cdr lst)) ) ) ) (defun LM:GetOddDupes ( lst ) ;; © Lee Mac 2010 (vl-remove-if-not '(lambda ( x ) (= 1 (boole 1 1 (cdr x)))) (LM:ListDupes lst) ) ) (LM:GetOddDupes my_lst)) Quote
Lee Mac Posted July 7, 2010 Posted July 7, 2010 Your list has only one element that is repeated twice - and hence it is omitted, as per your request. Quote
sadhu Posted July 7, 2010 Author Posted July 7, 2010 My list has six elements with "4" repeated twice(even) so it should be excluded while 1, 2, 3 and 5 are present only once(odd) so they should be included : (setq my_lst (list 1 2 3 4 4 5)) I tried this way too and I still get nil: (setq my_lst (list "1" "2" "3" "4" "4" "5")) Sorry if I wasn't clear. Quote
Lee Mac Posted July 7, 2010 Posted July 7, 2010 Ah - I thought you were counting only duplicates - my code ignores anything not repeated more than once. Quote
Lee Mac Posted July 7, 2010 Posted July 7, 2010 That makes my code much simpler: (defun LM:ListOccurrences ( lst ) ;; © Lee Mac 2010 (if lst (cons (cons (car lst) (- (length lst) (length (vl-remove (car lst) lst))) ) (LM:ListOccurrences (vl-remove (car lst) lst)) ) ) ) (defun LM:GetOddOccurrences ( lst ) ;; © Lee Mac 2010 (vl-remove-if-not '(lambda ( x ) (= 1 (boole 1 1 (cdr x)))) (LM:ListOccurrences lst) ) ) Quote
sadhu Posted July 7, 2010 Author Posted July 7, 2010 Yes , now I got it. It works. Thanks a lot Lee. Quote
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.