|
|||
|
In article
<43542a94-44bf-46b7-a761-9f2fe4ed6e01@z28g2000prd.googlegroups.com>, "joswig@corporate-world.lisp.de" <joswig@corporate-world.lisp.de> wrote: > > (defun accum-pairlist (mylist) > > (let ((return-list nil) > > (list (copy-tree mylist))) > > (dolist (li list) > > (if (assoc (first li) return-list) > > (setf (second (assoc (first li) return-list)) > > (+ > > (second (assoc (first li) return-list)) > > (second li))) > > (pushnew li return-list))) > > return-list)) > > > > //still a newbie > > (defun accum-pairlist (pl &aux rl) > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > (pushnew (list a1 0) rl)))) a2)) > rl) (defun accum-pairlist (pl &aux rl) (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car (pushnew (list a1 0) rl)))) a2)) rl) -- http://lispm.dyndns.org/ |
|
|
||||
|
||||
|
|
|
|||
|
Rainer Joswig wrote:
> In article > <43542a94-44bf-46b7-a761-9f2fe4ed6e01@z28g2000prd.googlegroups.com>, > "joswig@corporate-world.lisp.de" <joswig@corporate-world.lisp.de> > wrote: > > > > (defun accum-pairlist (mylist) > > > (let ((return-list nil) > > > (list (copy-tree mylist))) > > > (dolist (li list) > > > (if (assoc (first li) return-list) > > > (setf (second (assoc (first li) return-list)) > > > (+ > > > (second (assoc (first li) return-list)) > > > (second li))) > > > (pushnew li return-list))) > > > return-list)) > > > > > > //still a newbie > > > > (defun accum-pairlist (pl &aux rl) > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > > (pushnew (list a1 0) rl)))) a2)) > > rl) > > (defun accum-pairlist (pl &aux rl) > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > (pushnew (list a1 0) rl)))) a2)) rl) I don't think that posting the same code twice makes it better. And I don't think that the bloated thing called loop is needed. Ruby: list = [1,2],[3,4],[5,6],[1,7] accum_pairlist = proc{|pl| pl.inject([]){|a,e| pr=a.assoc(e[0]) and a[a.index(pr)][1] += e[1] or a << e.dup; a}} p accum_pairlist[ list ] p accum_pairlist[ list ] --- output --- [[1, 9], [3, 4], [5, 6]] [[1, 9], [3, 4], [5, 6]] But why not just use a hash-list? h = Hash.new(0) list.each{|k,v| h[k] += v } p h.sort |
|
|||
|
On Nov 11, 10:59 am, Rainer Joswig <jos...@lisp.de> wrote:
> In article > <43542a94-44bf-46b7-a761-9f2fe4ed6...@z28g2000prd.googlegroups.com>, > "jos...@corporate-world.lisp.de" <jos...@corporate-world.lisp.de> > > > > wrote: > > > (defun accum-pairlist (mylist) > > > (let ((return-list nil) > > > (list (copy-tree mylist))) > > > (dolist (li list) > > > (if (assoc (first li) return-list) > > > (setf (second (assoc (first li) return-list)) > > > (+ > > > (second (assoc (first li) return-list)) > > > (second li))) > > > (pushnew li return-list))) > > > return-list)) > > > > //still a newbie > > > (defun accum-pairlist (pl &aux rl) > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > > (pushnew (list a1 0) rl)))) a2)) > > rl) > > (defun accum-pairlist (pl &aux rl) > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car (pushnew (list a1 0) rl)))) a2)) > rl) > > --http://lispm.dyndns.org/ I was thinking along the same lines but wanted something that had a little more english. (defun value (key alist) (second (assoc key alist))) (defun (setf value) (val key alist) (setf (second (assoc key alist)) val)) (defun accum-pairlist (the-list) (loop for (key val) in the-list when (assoc key accum) do (incf (value key accum) val) else collect (list key val) into accum end finally (return accum))) |
|
|||
|
"William James" <w_a_x_man@yahoo.com> wrote on Tue, 11 Nov 2008:
> it seems that Xah Lee was right and you were wrong. Lisp processing in > archaic Lisp is more difficult than it is in a modern language. Please confine your comments to the technical aspects of what you are discussing. Every programming language is full of tradeoffs, and each such choice has both pros and cons. It is factually not the case that Lisp's choices in this matter were made in a state of ignorance, and that "everybody knows" today how to do it better. Using loaded terms like "archaic" and "modern" serves no purpose other than to add needless acrimony to an otherwise useful discussion. And please, whatever you do, don't take the style of the Mighty Xah as someone to emulate. The world isn't big enough for two of them. Given the volumes of his postings and writings, I fear that a second one may well clog up the remaining capacity of the internet's tubes. -- Don __________________________________________________ _____________________________ Don Geddis http://don.geddis.org/ don@geddis.org Incompetence: When you earnestly believe you can compensate for a lack of skill by doubling your efforts, there's no end to what you can't do. -- Despair.com |
|
|||
|
In article
<73612098-4a87-4c8d-ab51-f26348ff338b@e38g2000prn.googlegroups.com>, "Thomas M. Hermann" <tmh.public@gmail.com> wrote: > On Nov 11, 10:59 am, Rainer Joswig <jos...@lisp.de> wrote: > > In article > > <43542a94-44bf-46b7-a761-9f2fe4ed6...@z28g2000prd.googlegroups.com>, > > "jos...@corporate-world.lisp.de" <jos...@corporate-world.lisp.de> > > > > > > > > wrote: > > > > (defun accum-pairlist (mylist) > > > > (let ((return-list nil) > > > > (list (copy-tree mylist))) > > > > (dolist (li list) > > > > (if (assoc (first li) return-list) > > > > (setf (second (assoc (first li) return-list)) > > > > (+ > > > > (second (assoc (first li) return-list)) > > > > (second li))) > > > > (pushnew li return-list))) > > > > return-list)) > > > > > > //still a newbie > > > > > (defun accum-pairlist (pl &aux rl) > > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > > > (pushnew (list a1 0) rl)))) a2)) > > > rl) > > > > (defun accum-pairlist (pl &aux rl) > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car (pushnew (list a1 0) rl)))) a2)) > > rl) > > > > --http://lispm.dyndns.org/ > > I was thinking along the same lines but wanted something that had a > little more english. > > (defun value (key alist) > (second (assoc key alist))) > > (defun (setf value) (val key alist) > (setf (second (assoc key alist)) val)) > > (defun accum-pairlist (the-list) > (loop for (key val) in the-list > when (assoc key accum) do (incf (value key accum) val) > else collect (list key val) into accum end > finally (return accum))) Yes, but you also would want to get rid of calling ASSOC twice for each list element. -- http://lispm.dyndns.org/ |
|
|||
|
On Nov 11, 12:16 pm, Rainer Joswig <jos...@lisp.de> wrote:
> In article > <73612098-4a87-4c8d-ab51-f26348ff3...@e38g2000prn.googlegroups.com>, > "Thomas M. Hermann" <tmh.pub...@gmail.com> wrote: > > > > > On Nov 11, 10:59 am, Rainer Joswig <jos...@lisp.de> wrote: > > > In article > > > <43542a94-44bf-46b7-a761-9f2fe4ed6...@z28g2000prd.googlegroups.com>, > > > "jos...@corporate-world.lisp.de" <jos...@corporate-world.lisp.de> > > > > wrote: > > > > > (defun accum-pairlist (mylist) > > > > > (let ((return-list nil) > > > > > (list (copy-tree mylist))) > > > > > (dolist (li list) > > > > > (if (assoc (first li) return-list) > > > > > (setf (second (assoc (first li) return-list)) > > > > > (+ > > > > > (second (assoc (first li) return-list)) > > > > > (second li))) > > > > > (pushnew li return-list))) > > > > > return-list)) > > > > > > //still a newbie > > > > > (defun accum-pairlist (pl &aux rl) > > > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > > > > (pushnew (list a1 0) rl)))) a2)) > > > > rl) > > > > (defun accum-pairlist (pl &aux rl) > > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car (pushnew (list a1 0) rl)))) a2)) > > > rl) > > > > --http://lispm.dyndns.org/ > > > I was thinking along the same lines but wanted something that had a > > little more english. > > > (defun value (key alist) > > (second (assoc key alist))) > > > (defun (setf value) (val key alist) > > (setf (second (assoc key alist)) val)) > > > (defun accum-pairlist (the-list) > > (loop for (key val) in the-list > > when (assoc key accum) do (incf (value key accum) val) > > else collect (list key val) into accum end > > finally (return accum))) > > Yes, but you also would want to get rid of calling ASSOC twice for each list element. > > --http://lispm.dyndns.org/ Hmmm, I guess it could look like this. (defun accumulate (key val alist) (let ((pair (assoc key alist))) (when pair (incf (second pair) val)))) (defun accum-pairlist (the-list) (loop for (key val) in the-list unless (accumulate key val accum) collect (list key val) into accum end finally (return accum))) Doesn't read half bad. |
|
|||
|
On Mon, 10 Nov 2008 22:30:58 -0800 (PST), JonathanSmith415@gmail.com
wrote: >On Nov 10, 6:16*pm, "xah...@gmail.com" <xah...@gmail.com> wrote: >>stuff > >You clearly never took the time to learn lisp, and no one understands >your argument because you write in a terrible style. Xah uses Emacs Lisp - not Common Lisp - and everything he thinks he knows about Lisp is based on it. That he programs badly regardless is a topic for another time. George |
|
|||
|
In article
<734888b3-0bed-4047-a22e-6a0b81c62384@c2g2000pra.googlegroups.com>, "Thomas M. Hermann" <tmh.public@gmail.com> wrote: > On Nov 11, 12:16 pm, Rainer Joswig <jos...@lisp.de> wrote: > > In article > > <73612098-4a87-4c8d-ab51-f26348ff3...@e38g2000prn.googlegroups.com>, > > "Thomas M. Hermann" <tmh.pub...@gmail.com> wrote: > > > > > > > > > On Nov 11, 10:59 am, Rainer Joswig <jos...@lisp.de> wrote: > > > > In article > > > > <43542a94-44bf-46b7-a761-9f2fe4ed6...@z28g2000prd.googlegroups.com>, > > > > "jos...@corporate-world.lisp.de" <jos...@corporate-world.lisp.de> > > > > > > wrote: > > > > > > (defun accum-pairlist (mylist) > > > > > > (let ((return-list nil) > > > > > > (list (copy-tree mylist))) > > > > > > (dolist (li list) > > > > > > (if (assoc (first li) return-list) > > > > > > (setf (second (assoc (first li) return-list)) > > > > > > (+ > > > > > > (second (assoc (first li) return-list)) > > > > > > (second li))) > > > > > > (pushnew li return-list))) > > > > > > return-list)) > > > > > > > > //still a newbie > > > > > > > (defun accum-pairlist (pl &aux rl) > > > > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car > > > > > (pushnew (list a1 0) rl)))) a2)) > > > > > rl) > > > > > > (defun accum-pairlist (pl &aux rl) > > > > (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car (pushnew (list a1 0) rl)))) a2)) > > > > rl) > > > > > > --http://lispm.dyndns.org/ > > > > > I was thinking along the same lines but wanted something that had a > > > little more english. > > > > > (defun value (key alist) > > > (second (assoc key alist))) > > > > > (defun (setf value) (val key alist) > > > (setf (second (assoc key alist)) val)) > > > > > (defun accum-pairlist (the-list) > > > (loop for (key val) in the-list > > > when (assoc key accum) do (incf (value key accum) val) > > > else collect (list key val) into accum end > > > finally (return accum))) > > > > Yes, but you also would want to get rid of calling ASSOC twice for each list element. > > > > --http://lispm.dyndns.org/ > > Hmmm, I guess it could look like this. > > (defun accumulate (key val alist) > (let ((pair (assoc key alist))) > (when pair (incf (second pair) val)))) > > (defun accum-pairlist (the-list) > (loop for (key val) in the-list > unless (accumulate key val accum) > collect (list key val) into accum end > finally (return accum))) > > Doesn't read half bad. Looks good. In my version PUSHNEW can be reduced to PUSH. (defun accum-pairlist (pl &aux rl) (loop for (a1 a2) in pl do (incf (cadr (or (assoc a1 rl) (car (push (list a1 0) rl)))) a2)) rl) -- http://lispm.dyndns.org/ |
|
|||
|
On Nov 10, 6:01*am, r...@rpw3.org (Rob Warnock) wrote:
> Mark Carter <m...@privacy.net> wrote: > > +--------------- > | Suppose I have: (defvar *list* '((1 2) (3 4) (5 6) (1 7))) > | Now, suppose I want the "keys" of the list, defined by the first element > | of the list. Is there a Lisp function which is callable something like: > | (keys *list* :key #'first) ; => '(1 3 5) > +--------------- > > Uh... What's wrong with just (MAPCAR #'FIRST *LIST*)? > [Oh, and your example output is wrong...] > > +--------------- > | Suppose further that I want to accumulate totals based on keys. The > | first element in the list is the key, and the second element in the list > | is the value. Is there a Lisp function which is callable something like: > | (accum *list*) ; => '( (1 9) (3 4) (5 6) ) > +--------------- > > If the lists were really, *really* big, with lots of duplicate keys, > I'd probably use a hash table to store keys & sums. Otherwise I'd just > use a dumb, simple, N^2 cost insertion sum. You know, something like this: > > * * > (defun accum-by-key (list) > * * * * (loop with result = nil > * * * * * * * for (first second) in list > * * * * * do (let ((found (find first result :key #'first))) > * * * * * * * *(if found > * * * * * * * * *(incf (second found) second) > * * * * * * * * *(push (list first second) result))) > * * * * * finally (return (reverse result)))) > > * * ACCUM-BY-KEY > * * > (accum-by-key *list*) > > * * ((1 9) (3 4) (5 6)) > * * > > > -Rob > The hash table idea seems simpler to me. (defun accumulate-by-key (pairs) (let ((hash (make-hash-table))) (loop for (key value) in pairs do (incf (gethash key hash 0) value)) (loop for key being the hash-keys of hash using (hash-value value) collect (list key value)))) |
|
|||
|
On Nov 11, 11:31*am, "William James" <w_a_x_...@yahoo.com> wrote:
> Rob Warnock wrote: > > <JonathanSmith...@gmail.com> wrote: > > +--------------- > > | Mark Carter <m...@privacy.net> wrote: > > | > Suppose further that I want to accumulate totals based on keys. > > The | > first element in the list is the key, and the second element > > in the list | > is the value. Is there a Lisp function which is > > callable something like: *| > (accum list) ; => '( (1 9) (3 4) (5 6) ) > > > > *(defun accum-pairlist (list) > > > * *(let ((return-list nil)) > > > * * *(dolist (li list) > > > * * * *(if (assoc (first li) return-list) > > > * * * * * *(setf (second (assoc (first li) return-list)) > > > * * * * * * * * *(+ > > > * * * * * * * * * (second (assoc (first li) return-list)) > > > * * * * * * * * * (second li))) > > > * * * * *(pushnew li return-list))) > > > * * *return-list)) > > +--------------- > > > Careful!! Your solution has the same bug that my first > > (and, thankfully, unpublished!) version I did -- it doesn't > > give the same answer twice. [And why it behaves that way > > is even more serious!!] *E.g.: > > > * * > (defvar list '((1 2) (3 4) (5 6) (1 7))) > > > * * LIST > > * * > (accum-pairlist list) > > > * * ((5 6) (3 4) (1 9)) > > * * > (accum-pairlist list) > > > * * ((5 6) (3 4) (1 16)) > > * * > (accum-pairlist list) > > > * * ((5 6) (3 4) (1 23)) > > Well, Jonathan, it seems that Xah Lee was right and you were > wrong. *Lisp processing in archaic Lisp is more difficult than > it is in a modern language. > > Ruby: > > def accum_pairlist list > * accum = [] > * list.each{ |key,val| > * * pair = accum.assoc(key) *and > * * accum[accum.index(pair)][1] += val *or > * * accum << [key,val] } > * accum > end > > p accum_pairlist( list ) > p accum_pairlist( list ) > > --- output --- > [[1, 9], [3, 4], [5, 6]] > [[1, 9], [3, 4], [5, 6]] I don't see how my making an error using destructive functions puts lisp in the doghouse. I never argued that lisp was the be-all and end-all of basic list processing. Xah Lee argued that it was terrible for it. His arguments come from a fundamental lack of knowledge about lisp and lisp implementations (He thinks lisp doesn't have things that it does have, he assumes that cons structures in modern lisp implementations are implemented in the same way as they were in the 1960s). He also argued (through a misunderstanding of what a macro is), that lisp has irregular syntax structure.... (defun fn-pairlist (mylist fn) (let ((return-list nil) (list (copy-tree mylist))) (print fn) (dolist (li list) (if (assoc (first li) return-list) (setf (second (assoc (first li) return-list)) (apply fn (list (second (assoc (first li) return-list)) (second li)))) (pushnew li return-list))) (reverse return-list))) (defun accum-pairlist (mylist) (fn-pairlist mylist #'+)) (defun gcd-pairlist (mylist) (fn-pairlist mylist #'gcd)) (defun lcm-pairlist (mylist) (fn-pairlist mylist #'lcm)) (defun subtract-pairlist (mylist) (fn-pairlist mylist #'-)) (defun list-pairlist (mylist) (fn-pairlist mylist #'(lambda (a b) (if (listp a) (append a b) (list a b)) ))) You can expand it to fit whatever requirements you happen to have. |
|
|||
|
> (defun list-pairlist (mylist) > * (fn-pairlist mylist #'(lambda (a b) > * * * * * * * * * * * * * (if (listp a) > * * * * * * * * * * * * * * * (append a b) > * * * * * * * * * * * * * * * (list a b)) > * * * * * * * * * * * * * ))) > > You can expand it to fit whatever requirements you happen to have. (defun list-pairlist (mylist) (fn-pairlist mylist #'(lambda (a b) (if (listp a) (if (listp b) (append a b) (append a (list b))) (list a b)) ))) (I'm terrible and forgetful) |
|
|||
|
On Nov 11, 3:17*pm, JonathanSmith...@gmail.com wrote:
> On Nov 11, 11:31*am, "William James" <w_a_x_...@yahoo.com> wrote: > > > > > > > Rob Warnock wrote: > > > <JonathanSmith...@gmail.com> wrote: > > > +--------------- > > > | Mark Carter <m...@privacy.net> wrote: > > > | > Suppose further that I want to accumulate totals based on keys. > > > The | > first element in the list is the key, and the second element > > > in the list | > is the value. Is there a Lisp function which is > > > callable something like: *| > (accum list) ; => '( (1 9) (3 4) (56) ) > > > > > *(defun accum-pairlist (list) > > > > * *(let ((return-list nil)) > > > > * * *(dolist (li list) > > > > * * * *(if (assoc (first li) return-list) > > > > * * * * * *(setf (second (assoc (first li) return-list)) > > > > * * * * * * * * *(+ > > > > * * * * * * * * * (second (assoc (first li) return-list)) > > > > * * * * * * * * * (second li))) > > > > * * * * *(pushnew li return-list))) > > > > * * *return-list)) > > > +--------------- > > > > Careful!! Your solution has the same bug that my first > > > (and, thankfully, unpublished!) version I did -- it doesn't > > > give the same answer twice. [And why it behaves that way > > > is even more serious!!] *E.g.: > > > > * * > (defvar list '((1 2) (3 4) (5 6) (1 7))) > > > > * * LIST > > > * * > (accum-pairlist list) > > > > * * ((5 6) (3 4) (1 9)) > > > * * > (accum-pairlist list) > > > > * * ((5 6) (3 4) (1 16)) > > > * * > (accum-pairlist list) > > > > * * ((5 6) (3 4) (1 23)) > > > Well, Jonathan, it seems that Xah Lee was right and you were > > wrong. *Lisp processing in archaic Lisp is more difficult than > > it is in a modern language. > > > Ruby: > > > def accum_pairlist list > > * accum = [] > > * list.each{ |key,val| > > * * pair = accum.assoc(key) *and > > * * accum[accum.index(pair)][1] += val *or > > * * accum << [key,val] } > > * accum > > end > > > p accum_pairlist( list ) > > p accum_pairlist( list ) > > > --- output --- > > [[1, 9], [3, 4], [5, 6]] > > [[1, 9], [3, 4], [5, 6]] > > I don't see how my making an error using destructive functions puts > lisp in the doghouse. > > I never argued that lisp was the be-all and end-all of basic list > processing. Xah Lee argued that it was terrible for it. His arguments > come from a fundamental lack of knowledge about lisp and lisp > implementations (He thinks lisp doesn't have things that it does have, > he assumes that cons structures in modern lisp implementations are > implemented in the same way as they were in the 1960s). He also argued > (through a misunderstanding of what a macro is), that lisp has > irregular syntax structure.... > > (defun fn-pairlist (mylist fn) > * (let ((return-list nil) > * * * * (list (copy-tree mylist))) > * * (print fn) > * * (dolist (li list) > * * * (if (assoc (first li) return-list) > * * * * * (setf (second (assoc (first li) return-list)) > * * * * * * * * (apply fn > * * * * * * * * * * * *(list > * * * * * * * * * * * * *(second (assoc (first li) return-list)) > * * * * * * * * * * * * *(second li)))) > * * * * * (pushnew li return-list))) > * * (reverse return-list))) > > (defun accum-pairlist (mylist) > * (fn-pairlist mylist #'+)) > > (defun gcd-pairlist (mylist) > * (fn-pairlist mylist #'gcd)) > > (defun lcm-pairlist (mylist) > * (fn-pairlist mylist #'lcm)) > > (defun subtract-pairlist (mylist) > * (fn-pairlist mylist #'-)) > > (defun list-pairlist (mylist) > * (fn-pairlist mylist #'(lambda (a b) > * * * * * * * * * * * * * (if (listp a) > * * * * * * * * * * * * * * * (append a b) > * * * * * * * * * * * * * * * (list a b)) > * * * * * * * * * * * * * ))) > > You can expand it to fit whatever requirements you happen to have.- Hide quoted text - Friends, Programming languages only exist to match the programmers mental model of a program to the nearly non-existent ability of machines to understand it. It follows that complaints about language features are really reflections of individual intellectual styles, abilities, and limitations. Truly good programmers are so nimble in their thinking that language features don't even reach the level of consciousness; their ideas are bigger and more abstract. Consequently, those who engage in language criticism are mostly revealing their shortcomings. Refutations and defenses are, in turn, wasteful, bordering on self- destructive. |
|
|||
|
On 2008-11-11 17:48:45 -0500, Gene <gene.ressler@gmail.com> said:
> It follows that complaints about language features are > really reflections of individual intellectual styles, abilities, and > limitations. Complaints about a language are valid when they reflect the real limitations of that language. If a feature is missing from a language then it is legitimate to complain about having to greenspun it, or worse still, the language's inability to let you greenspun it short of implementing a full blown interpreter for some other, more featureful language. |
|
|||
|
On Nov 11, 6:49*pm, Raffael Cavallaro <raffaelcavallaro@pas-d'espam-
s'il-vous-plait-mac.com> wrote: > On 2008-11-11 17:48:45 -0500, Gene <gene.ress...@gmail.com> said: > > > It follows that complaints about language features are > > really reflections of individual intellectual styles, abilities, and > > limitations. > > Complaints about a language are valid when they reflect the real > limitations of that language. If a feature is missing from a language > then it is legitimate to complain about having to greenspun it, or > worse still, the language's inability to let you greenspun it short of > implementing a full blown interpreter for some other, more featureful > language. Ah, but you describe objective critism, which of course is good and useful. Complaint is about personal discontent. Spending intellectual and emotional energy on the merits of conses ... yikes. |
|
|||
|
Rob Warnock wrote:
> <JonathanSmith415@gmail.com> wrote: > +--------------- > | Mark Carter <m...@privacy.net> wrote: > | > Suppose further that I want to accumulate totals based on keys. The > | > first element in the list is the key, and the second element in the list > | > is the value. Is there a Lisp function which is callable something like: > | > (accum *list*) ; => '( (1 9) (3 4) (5 6) ) > | > | (defun accum-pairlist (list) > | (let ((return-list nil)) > | (dolist (li list) > | (if (assoc (first li) return-list) > | (setf (second (assoc (first li) return-list)) > | (+ > | (second (assoc (first li) return-list)) > | (second li))) > | (pushnew li return-list))) > | return-list)) > +--------------- > > Careful!! Your solution has the same bug that my first > (and, thankfully, unpublished!) version I did -- it doesn't > give the same answer twice. [And *why* it behaves that way > is even *more* serious!!] When I see such mistakes (and I make them too), I can't help mentioning how easy it is to do such things given a well chosen set of higher order functions. For example in q: q) f: {sum each x[;1] @ group x[;0]} q) f (1 2;3 4;5 6;1 7) 1| 9 3| 4 5| 6 {..} is lambda, by default x names its first arg. x[;0] selects column 0 of x: 1 3 5 1 x[;1] selects column 1 of x: 2 4 6 7 group x[;0] returns a dictionary, where keys are 1, 3, 5, and corresponding values are *indices* where the keys occur in x[;1]. q) group 1 3 5 1 1| 0 3 3| ,1 // singleton lists are shown with a leading , 5| ,2 x @ group y selects values from list x as per indices in y. The result has the same shape as y. If y is a dictionary, so is the result. q) 2 4 6 7 @ group 1 3 5 1 // select indexed values 1| 2 7 3| ,4 5| ,6 f each x applies function f to each element of list x, returning a list, or if x is a dictionary, f applies f to each value, returning a dictionary. q) sum each 2 4 6 7 @ group 1 3 5 1 1| 9 3| 4 5| 6 Now, I don't expect anyone to switch to q but some of its ideas are worth expressing in lisp. each is basically an extension of map to dictionaries. group uses the default equality function for the list element type. Returning indices instead of values is quite useful because they can then be used for selecting elements from another list. One reason I prefer such higher order functions is because one easily see how similar patterns are useful in different contexts (this gets lost in low level bitbanging code). As an example the "list1 @ group list2" idiom in f can be used to create an inverted file index. If file foo contains <term> <filename> per line: term1 file1 term2 file2 term3 file1 term1 file2 term3 file3 In q I can read this in like so: q) tf: ("SS", " ")0: `:foo // read data from foo. two symbols per line q) tf term1 term2 term3 term1 term3 // row0 contains the first field file1 file1 file1 file2 file3 // row1 contains the second field Now an inverted index is simply: q) invidx: tf[1] @ group tf[0] q) invidx term1| `file1`file2 term2| ,`file2 term3| `file1`file3 q) invidx `term3 // use it to look up which files contain term3 `file1`file3 |
|
|
![]() |
| Thread Tools | |
| Display Modes | |
|
|
Similar Threads
|
||||
| Thread | Thread Starter | Forum | Replies | Last Post |
| Re: SAS macro: is there a function to return the number of items | Joe Whitehurst | Newsgroup comp.soft-sys.sas | 0 | 04-17-2008 04:20 AM |
| Re: tip: list processing: SQL into list or call execute | Fehd, Ronald J. | Newsgroup comp.soft-sys.sas | 0 | 02-27-2008 12:56 PM |
| Re: tip: list processing: SQL into list or call execute | Chang Chung | Newsgroup comp.soft-sys.sas | 1 | 02-26-2008 07:32 PM |
| Re: list processing: SQL into list or call execute | Mike Rhoads | Newsgroup comp.soft-sys.sas | 0 | 02-26-2008 07:13 PM |
| tip: list processing: SQL into list or call execute | Fehd, Ronald J. | Newsgroup comp.soft-sys.sas | 0 | 02-26-2008 01:42 PM |