Is there a List comprehensions macro?

Q&A's, tips, howto's
jopython
Posts: 123
Joined: Tue Sep 14, 2010 3:08 pm

Is there a List comprehensions macro?

Is there a macro or library for list comprehensions in newlisp?

Something like this small one liner (eg in python) can come real handy.

Code: Select all

``````>>> a = range(10)
>>> b = range(11,20)
>>> [[x, y] for x in b for y in a]
``````
Which gives

Code: Select all

``````[[11, 0], [11, 1], [11, 2], [11, 3], ......
``````

cormullion
Posts: 2037
Joined: Tue Nov 29, 2005 8:28 pm
Location: latiitude 50N longitude 3W
Contact:

Re: Is there a List comprehensions macro?

Not sure, I don't think it does. Of course you can easily say:

Code: Select all

``(dolist (x b) (dolist (y a) (push (list x y) results -1)))``
but presumably this isn't a list comprehension, just a nested list iteration. Although I glanced through the Wikipedia entry and the Rosetta code examples, I didn't get the concept... Do you have any examples that couldn't be simply written as list iteration?

jopython
Posts: 123
Joined: Tue Sep 14, 2010 3:08 pm

Re: Is there a List comprehensions macro?

To me, it is a 'for' loop inside a 'for' loop if you come from C-like languages and then mutate the crap of those arrays. Besides multilevel 'for' loops make my head ache :(

newBert
Posts: 149
Joined: Fri Oct 28, 2005 5:33 pm
Location: France

Re: Is there a List comprehensions macro?

Here are some comparisons between Python and NewLisp that I made a long time ago:

Code: Select all

``````;; List Comprehensions in PYTHON

;;>>> vec = [2, 4, 6]
;;>>> [3*x for x in vec]
;;[6, 12, 18]

(set 'vec '(2 4 6))
(println (map (lambda (x) (* x 3)) vec))
;-> (6 12 18)

;;>>> vec = [2, 4, 6]
;;>>> [[x, x**2] for x in vec]
;;[[2, 4], [4, 16], [6, 36]]

(println (map (lambda (x) (list x (pow x))) vec))
;-> ((2 4) (4 16) (6 36))

;;>>> freshfruit = ['  banana', '  loganberry ', 'passion fruit  ']
;;>>> [weapon.strip() for weapon in freshfruit]
;;['banana', 'loganberry', 'passion fruit']

(set 'freshfruit '("  banana" "  loganberry " "passion fruit  "))
(println (map trim freshfruit))
;-> ("banana" "loganberry" "passion fruit")

;;>>> [3*x for x in vec if x > 3]
;;[12, 18]
;;>>> [3*x for x in vec if x < 2]
;;[]

(println (map (lambda (x) (when (> x 3)(* x 3)))vec))
;-> (nil 12 18)
(println (map (lambda (x) (when (< x 2)(* x 3))) vec))
;-> (nil nil nil)

;;>>> vec1 = [2, 4, 6]
;;>>> vec2 = [4, 3, -9]
;;>>> [x*y for x in vec1 for y in vec2]
;;[8, 6, -18, 16, 12, -36, 24, 18, -54]

(set 'vec1 '(2 4 6))
(set 'vec2 '(4 3 -9))
(dolist (x vec1)(dolist (y vec2)(print (* x y) " ")))
(println)
;-> 8 6 -18 16 12 -36 24 18 -54

;;>>> [x+y for x in vec1 for y in vec2]
;;[6, 5, -7, 8, 7, -5, 10, 9, -3]

(dolist (x vec1)(dolist (y vec2)(print (+ x y) " ")))
(println)
;-> 6 5 -7 8 7 -5 10 9 -3

;;>>> [vec1[i]*vec2[i] for i in range(len(vec1))]
;;[8, 12, -54]

(println (map * vec1 vec2))
;-> (8 12 -54)

;;>>> mat = [
;;...        [1, 2, 3],
;;...        [4, 5, 6],
;;...        [7, 8, 9],
;;...       ]
;;>>> print([[row[i] for row in mat] for i in [0, 1, 2]])
;;[[1, 4, 7], [2, 5, 8], [3, 6, 9]]
;; ou
;;>>> list(zip(*mat))
;;[(1, 4, 7), (2, 5, 8), (3, 6, 9)]

(set 'matrix '((1 2 3)(4 5 6)(7 8 9)))
(println (transpose matrix))
;-> ((1 4 7) (2 5 8) (3 6 9))

;;for i in [0, 1, 2]:
;;    for row in mat:
;;        print(row[i], end="")
;;    print()

(dolist (row (transpose matrix)) (println row))
;-> (1 4 7)
;   (2 5 8)
;   (3 6 9)
``````
BertrandnewLISP v.10.7.6 64-bit on Linux (Peppermint 9)