List of list... how to add to existing list another list?

List of list... how to add to existing list another list?

Buzz0m
Collaborator Collaborator
3,473 Views
8 Replies
Message 1 of 9

List of list... how to add to existing list another list?

Buzz0m
Collaborator
Collaborator

Hi,

I've been hitting a wall for a while and can't seem to wrap my cognition around the examples available on the net...

How should a list of lists be created with autolisp? Eg. if i have a list of coordinates, how do i add new coordinates to that list?

 

Below is a basic example with coordinates. The goal would be to get a new list of lists, with only certain instances of the original list...

 

I've tried cons and append, but there something funky with my syntax, because I cant seem to get a list of lists, but something else. Also when I'm looping with foreach and try to add the "looping" entity to the list I can't seem to get the list values of the "looping entity" to be added but rather the name of the "looping entity"... in the example that would be "point"...

 

Any help is greatly appreciated 😃

- F

 

PS. the example is just a easy case example. To create a list of coordinates is not my actual goal...

 

(setq Coords (List
	'(123 -50 10)
	'(124 50 -13)
	'(223 -150 120)
	'(123 -1.50 -10)
)

(setq CoordsBelowZero '())

(foreach point Coords 
	(setq z (nth 2 point))
        (if (< z 0)
            (setq CoordsBelowZero '(CoordsBelowZero point)
;how should a list of list be expanded or created? ) )

;goal: ((123 -1.50 -10) (124 50 -13))
0 Likes
Accepted solutions (2)
3,474 Views
8 Replies
Replies (8)
Message 2 of 9

pbejse
Mentor
Mentor
Accepted solution
(foreach point Coords 
        (if (< (caddr  point) 0)
            	(setq CoordsBelowZero (cons point CoordsBelowZero)))
       )
0 Likes
Message 3 of 9

_gile
Consultant
Consultant

Hi,

 

Higher order functions are your friends

 

You can define a function which check if Z is below zero :

(defun belowZero (p) (< (caddr p) 0))

The you can use this function as argument with vl-remove-if-not (the function name is safe explanatory):

(setq CoordsBelowZero (vl-remove-if-not 'belowZero coords))

In real life, we do not need to define such function as 'belowZero', we often prefer use a lambda expression (i.e. an anonymous function)

(setq CoordsBelowZero (vl-remove-if-not '(lambda (p) (< (caddr p) 0)) coords))


Gilles Chanteau
Programmation AutoCAD LISP/.NET
GileCAD
GitHub

Message 4 of 9

ВeekeeCZ
Consultant
Consultant
Accepted solution

(setq new-lst (cons itm new-lst))

 

Some remarks worth to add to the solution above:

- simple, basic principle, very useful

- the order matters! has to be (cons item new-list), no other way around

- no need to prepare the empty list: (setq CoordsBelowZero '()) but you need to make sure that new-list is always nil (local varible or preset nil)

- returned list is backwards! Use (reverse new-list) in the end if you want to maintain the original order.

  

(setq Coords '((123 -50 10)
               (124 50 -13)
               (223 -150 120)
               (123 -1.50 -10)))

(foreach point Coords
  (setq z (nth 2 point))
  (if (< z 0)
    (setq CoordsBelowZero (cons point CoordsBelowZero ))))

(setq CoordsBelowZero (reverse CoordsBelowZero))

 

Or your example with append. The result is not reversed.

(defun c:test ( / CoordsBelowZero)

(setq Coords '((123 -50 10)
               (124 50 -13)
               (223 -150 120)
               (123 -1.50 -10)))

(foreach point Coords
  (setq z (nth 2 point))
  (if (< z 0)
    (setq CoordsBelowZero (append CoordsBelowZero (list point)))))

  )
Message 5 of 9

john.uhden
Mentor
Mentor

OR...

(defun Z>=0 (pt)
  (>= (caddr pt) 0)
)
(setq Coords<0 (vl-remove-if 'Z>=0 Coords))

John F. Uhden

0 Likes
Message 6 of 9

Buzz0m
Collaborator
Collaborator

thank you all for the really quick and on point answers! I knew my problem was basic but that you took the time to elaborate the alternatives and implications is really helpful!

 

I must have had the order of the item to add and the list wrong when I tried using cons earlier on! Thanks to all the examples on variations of list manipulation I got my other lisp to work! I'll post a link to another thread when the code is ready for scrutiny 😉

 

 Have a great weekend!

0 Likes
Message 7 of 9

martti.halminen
Collaborator
Collaborator

A style/performance point: APPEND is really slow as it needs to create a fresh copy of all of its arguments except the last one for every call. For just a few items  it doesn't matter, but if you are collecting thousands of points it will show. 

Typical Lisp idiom for collecting items in a loop is to use CONS instead of APPEND, and if needed, reverse the result when finished.

Generally, APPEND is rarely used in practice. For example I have an AutoLISP program consisting of 90000 lines of program code, there are only twelve APPEND calls in all of that.

 

-- 

0 Likes
Message 8 of 9

Buzz0m
Collaborator
Collaborator

I've been learning C# and the same performance problem is evident in that language. I'm guessing it is a universal characteristic of all "append"-methods/functions... thanks in any case for the heads up!

 

Here is a link to the lisp for which I originally needed the help with list creation. The lisp works, but is still a bit unrefined. There are some kinks that would need  to be ironed out, but I got it to do what I needed...

https://forums.autodesk.com/t5/visual-lisp-autolisp-and-general/change-all-to-color-bylayer-linetype...

 

Thanks again to all!

 

PS. @martti.halminen torilla tavataan 😉

0 Likes
Message 9 of 9

_gile
Consultant
Consultant

@Buzz0m wrote:

I've been learning C# and the same performance problem is evident in that language. I'm guessing it is a universal characteristic of all "append"-methods/functions... thanks in any case for the heads up!


The only data structure used in AutoLISP is the singly linked list (called list).

This kind of data structure is rarely used in .NET (except with F#) and is not at all the same as List<T> which is a resizable indexed array.



Gilles Chanteau
Programmation AutoCAD LISP/.NET
GileCAD
GitHub

0 Likes