TheSwamp
Code Red => AutoLISP (Vanilla / Visual) => Topic started by: A_LOTA_NOTA on November 29, 2010, 03:53:38 PM
-
I typically use a while loop with a counter when cycling through a selection set. I'm sure like most things this can be done a number of ways. So I was just curious to see how everyone else does it.
(setq ssmax (sslength ss))
(setq count 0)
(while (< count ssmax)
(setq en (ssname ss count) ed (entget en ))
)
-
Usually, something like:
(setq i -1)
(while (setq e (ssname ss (setq i (1+ i))))
...
)
Because it seems to be the fastest option uncompiled :-)
-
Another one:
(vl-remove-if 'listp (mapcar 'cadr (ssnamex (ssget))))
And one more:
(setq selset (ssget))
((lambda (/ tab item)
(repeat (setq tab nil
item (sslength selset)
) ;_ end setq
(setq tab (cons (ssname selset (setq item (1- item))) tab))
) ;_ end of repeat
) ;_ end of lambda
)
-
Same as Lee or:
(repeat (setq n (sslength ss))
(setq e (sname ss (setq n (1- n))))
...
)
depends my humor...
More, if I'm going the ActiveX route:
(vlax-for o (setq ss (vla-get-ActiveSelectionSet (vla-get-ActiveDocument (vlax-getacad-object))))
...
)
(vla-delete ss)
-
Lee,
mapcar-name
mapcar-lambda
can be fast as well; especially when put up against some "while-setq" situations.
I use them all but i start with a simple recursive process first (a lot of times its easier to think thru but...).
-
mapcar-name
mapcar-lambda
can be fast as well; especially when put up against some "while-setq" situations.
I do agree for most list operations, but in this case you lose a lot of speed with the ssnamex call... :|
-
I was thinking of using "repeat" and that’s lead to posting this question. I have seen some nice code posted with mapcar and lambda. Both I would like to use sometime but don’t know much about them.
-
@Lee
Sure; I'll have to take your word on that (I dont even remember what ssnamex does to be honest).
I did find this one by me in my ss-lib and one by Vladimir which i thought were very similar. the only difference i saw was that he counted down and i counted up *lol*. I found a bunch of others some with names (Giles, CAB, etc) but these two were the most similar--and i laughed a little-.
(defun sel2lst ( sel / l len )
;; By: Vladimir Nesterovsky
(if (= 'PICKSET (type sel))
(repeat (setq len (sslength sel))
(setq len (1- len) l (cons (ssname sel len) l)))))
;;or another alias for that
(setq sstol sel2lst)
(defun sset2-list (ss / lst cntr)
;; By: John K
(setq cntr 0)
(if (eq (type ss) 'PICKSET)
(repeat (sslength ss)
(setq lst
(append lst (list (list (ssname ss cntr)))))
(setq cntr (1+ cntr)))
'*ERROR* )
lst )
@A_LOTA_NOTA
what do you mean you dont know about them? what dont you know? ask away people are here to help.
-
I used to use ' while ' with ' ssdel '.
(while (setq Ent (ssname ss 0))
.......
(ssdel Ent)
)
Mostly now I use the way Lee shows, that I picked up from Alan ( CAB ).
-
Lately my choice has been:
(while ss
(setq item (ssname ss 0))
;Remainder of code here
(ssdel (ssname ss 0))
)
Saves the extra variable of a counter, of course this only works if you do not want to reuse the selection set in another loop.
-
Not conclusive, but quick speed test:
(defun _while ( ss / l i )
(setq i (sslength ss))
(while (<= 0 (setq i (1- i)))
(setq l (cons (ssname ss i) l))
)
)
(defun _while2 ( ss / l i e )
(setq i -1)
(while (setq e (ssname ss (setq i (1+ i))))
(setq l (cons e l))
)
)
(defun _mapcar ( ss )
(vl-remove-if (function listp)
(mapcar (function cadr) (ssnamex ss))
)
)
(defun _repeat ( ss / i l )
(repeat (setq i (sslength ss))
(setq l (cons (ssname ss (setq i (1- i))) l))
)
)
Uncompiled:
SSLength: 5000 Entities
Elapsed milliseconds / relative speed for 256 iteration(s):
(_WHILE2 SS).....1529 / 4.26 <fastest>
(_WHILE SS)......1763 / 3.70
(_REPEAT SS).....2074 / 3.14
(_MAPCAR SS).....6521 / 1.00 <slowest>
Compiled:
SSLength: 5000 Entities
Elapsed milliseconds / relative speed for 1024 iteration(s):
(_REPEAT SS)......1825 / 15.44 <fastest>
(_WHILE SS).......1841 / 15.30
(_WHILE2 SS)......1888 / 14.92
(_MAPCAR SS).....28174 / 1.00 <slowest>
-
@A_LOTA_NOTA
what do you mean you dont know about them? what dont you know? ask away people are here to help.
Thanks for the offer. After searching and finding the following threads I feel I have a better understanding.
http://www.theswamp.org/index.php?topic=340.0 (http://www.theswamp.org/index.php?topic=340.0)
http://www.theswamp.org/index.php?topic=2953.msg37000#msg37000+ (http://www.theswamp.org/index.php?topic=2953.msg37000#msg37000+)
-
Since most of my looping involves lists, I normally count backwards. This lets me put the (length...) function before the loop so it only gets called once rather than every loop (list size rarely changes) and I compare the index to a constant (typically -1) in the test. It also has the benefit of (cons...) calls internal to the loop keeping any resultant lists in the same order as the original without figuring where the (reverse...) call needs to be.
Recently I've had cases with *massive* lists which required iterating over the rest of the list to find matches. In these cases I work with a (while main_list (setq cur_obj (car main_list)) ... (setq main_list (cdr main_list))) format. The gradual reduction in list size improves speed but I consider it too complex for minor list management.
-
I use Lee's "While2" example.
-
I used to use ' while ' with ' ssdel '.
(while (setq Ent (ssname ss 0))
.......
(ssdel Ent)
)
Mostly now I use the way Lee shows, that I picked up from Alan ( CAB ).
I use the same way coz I have learned from you many moons ago :)
Regards
Oleg