- •Introduction
- •Who should read this book
- •How This Book Is Organized
- •How to Use This Book
- •Where to Find the LISP Programs
- •CHAPTER 1: Introducing AutoLISP
- •Understanding the Interpreter and Evaluation
- •The Components of an Expression
- •Using Arguments and Expressions
- •Using Variables
- •Understanding Data Types
- •Integers and Real Numbers
- •Strings
- •Lists
- •File Descriptors
- •Object Names
- •Selection Sets
- •Symbols
- •Subrs
- •Atoms
- •Assigning Values to Variables with Setq
- •Preventing Evaluation of Arguments
- •Applying Variables
- •Functions for Assigning Values to Variables
- •Adding Prompts
- •CHAPTER 2: Storing and Running Programs
- •Creating an AutoLISP Program
- •What you Need
- •Creating an AutoLISP File
- •Loading an AutoLISP file
- •Running a Loaded Program
- •Understanding How a Program Works
- •Using AutoCAD Commands in AutoLISP
- •How to Create a Program
- •Local and Global Variables
- •Automatic Loading of Programs
- •Managing Large Acad.lsp files
- •Using AutoLISP in a Menu
- •Using Script Files
- •CHAPTER 3: Organizing a Program
- •Looking at a Programs Design
- •Outlining Your Programming Project
- •Using Functions
- •Adding a Function
- •Reusing Functions
- •Creating an 3D Box program
- •Creating a 3D Wedge Program
- •Making Your Code More Readable
- •Using Prettyprint
- •Using Comments
- •Using Capitals and Lower Case Letters
- •Dynamic Scoping
- •CHAPTER 4: Interacting with the Drawing Editor
- •A Sample Program Using Getdist
- •How to Get Angle Values
- •Using Getangle and Getorient
- •How to Get Text Input
- •Using Getstring
- •Using Getkword
- •How to Get Numeric Values
- •Using Getreal and Getint
- •How to Control User Input
- •Using Initget
- •Prompting for Dissimilar Variable Types
- •Using Multiple Keywords
- •How to Select Groups of Objects
- •Using Ssget
- •A Sample Program Using Ssget
- •CHAPTER 5: Making Decisions with AutoLISP
- •Making Decisions
- •How to Test for Conditions
- •Using the If function
- •How to Make Several Expressions Act like One
- •How to Test Multiple Conditions
- •Using the Cond function
- •How to Repeat parts of a Program
- •Using the While Function
- •Using the Repeat Function
- •Using Test Expressions
- •CHAPTER 6: Working With Geometry
- •How to find Angles and Distances
- •Understanding the Angle, Distance, and Polar Functions
- •Using Trigonometry to Solve a Problem
- •Gathering Information
- •Finding Points Using Trigonometry
- •Functions Useful in Geometric Transformations
- •Trans
- •Atan
- •Inters
- •CHAPTER 7: Working with Text
- •Working With String Data Types
- •Searching for Strings
- •Converting a Number to a String
- •How to read ASCII text files
- •Using a File Import Program
- •Writing ASCII Files to Disk
- •Using a Text Export Program
- •CHAPTER 8: Interacting with AutoLISP
- •Reading and Writing to the Screen
- •Reading the Cursor Dynamically
- •Writing Text to the Status and Menu Areas
- •Calling Menus from AutoLISP
- •Drawing Temporary Images on the Drawing Area
- •Using Defaults in a Program
- •Adding Default Responses to your Program
- •Dealing with Aborted Functions
- •Using the *error* Function
- •Organizing Code to Reduce Errors
- •Debugging Programs
- •Common Programming Errors
- •Using Variables as Debugging Tools
- •CHAPTER 9: Using Lists to store data
- •Getting Data from a List
- •Using Simple Lists for Data Storage
- •Evaluating Data from an Entire List at Once
- •Using Complex Lists to Store Data
- •Using Lists for Comparisons
- •Locating Elements in a List
- •Searching Through Lists
- •Finding the Properties of AutoCAD Objects
- •Using Selection Sets and Object Names
- •Understanding the structure of Property Lists
- •Changing the properties of AutoCAD objects
- •Getting an Object Name and Coordinate Together
- •CHAPTER 10: Editing AutoCAD objects
- •Editing Multiple objects
- •Improving Processing Speed
- •Using Cmdecho to Speed up Your Program
- •Improving Speed Through Direct Database Access
- •Filtering Objects for Specific Properties
- •Filtering a Selection Set
- •Selecting Objects Based on Properties
- •Accessing AutoCAD's System Tables
- •CHAPTER 11: Accessing Complex Objects
- •Accessing Polyline Vertices
- •Defining a New Polyline
- •Drawing the new Polyline
- •Testing for Polyline Types
- •How Arcs are Described in Polylines
- •Accessing Object Handles and Block Attributes
- •Using Object Handles
- •Using Object Handles
- •Extracting Attribute Data
- •Appendix A: Menu Primer
- •Appendix B: Error Messages
- •Appendix C: Group Codes
The ABC’s of AutoLISP by George Omura
Chapter 9: Using Lists to store data
Introduction
Using an Element of a List as a Marker
Getting Data from a List
Finding the Properties of AutoCAD Objects
Using Simple Lists for Data Storage
Using Selection Sets and Object Names
Evaluating Data from an entire list at once
Understanding the Structure of Property Lists
Using Complex Lists for Data Storage
Changing the Properties of AutoCAD Objects
Using Lists for Comparisons
Getting Object Names and Coordinates Together
Location Elements in a List
Conclusion
Searching Through a List
Introduction
We mentioned that there are actually two classes of lists, those meant to be evaluated, which are called expressions or forms, and lists that are repositories for data such as a coordinate list. No matter what the type of list you are dealing with, you can manipulate lists to suite the needs of your program. In this section we will look at the general subject of lists and review some of the functions that allow you to manipulate them.
There are a several functions provided to access and manipulate lists in a variety of ways. You have already seen car and cdr. Table 9.1 shows a list of other functions with a brief description of their uses.
187
Copyright © 2001 George Omura,,World rights reserved
The ABC’s of AutoLISP by George Omura
Function
(mapcar function list list... )
(apply function list)
(foreach symbol list expression)
(reverse list)
(Cons element list)
(append list list ...)
(last list)
(length list)
(member element list)
(nth integer list)
Use
Apply elements of lists as arguments, to a function. Each element in the list is processed until the end of the list is reached
Apply the entire contents of a list to a function.
Sets individual elements of a list to symbol then evaluates an expression containing that symbol. Each element in the list is processed until the end of the list is reached.
reverses the order of elements in a list.
Adds a new first element to a list. The element can be any legal data type.
Takes any number of lists and combines their elements into one list.
Finds the last element of a list.
Finds the number of elements in a list.
Finds the remainder of a list starting with element.
Finds the element of a list where integer is the number of the desired element within the list. The first item in a list is number 0.
So far, we have concentrated on the use of lists as a means of structuring and building your programs. But lists can also be use as repositories for data. You have already seen how coordinate list are used to store the x and y coordinate values of a point. Lists used for storing data can be much larger than the coordinate example. Consider the mdist program you saw in chapter 5. This program uses the append function to constantly add values to a list. This list is then evaluated to obtain the sum of its contents (see figure 9.1).
(Defun C:MDIST (/ dstlst dst) (setq dstlst '(+ 0))
(while (setq dst (getdist "\nPick point or Return to exit: ")) (Setq dstlst (append dstlst (list dst)))
(princ (Eval dstlst))
)
)
Figure 9.1: The Mdist program
We have an example here of a list being both a repository of data and a form or a list that can be evaluated. This is accomplished by starting the list with a functions, in this case, the plus function. Each time a value is appended to
188
Copyright © 2001 George Omura,,World rights reserved
The ABC’s of AutoLISP by George Omura
the list, it is evaluated to get the sum of the numeric elements of that list.
Suppose your have a list that does not contain a function, but you want to apply some function to it. The following sections discusses ways you can use the functions listed in table 9.1 perform computations on lists.
Getting Data from a List
In the mdist program, a function was applied to a list to get the total of all the numbers in that list. Functions like plus, minus, multiply and divide accept multiple numeric values for arguments. But what if you want to apply a list to a function that will only take single atoms for arguments.
Using Simple Lists for Data Storage
Mapcar is used where you want to use a list as a queue for arguments to a function. It allows you to perform a recursive function on a list of items. For example, suppose you want the sequential numbering program from chapter 5 to place the numbers at points you manually select rather than in a straight line. Figure 9.2 shows a program that does this:
;Program to write sequential numbers -- Seqrand.lsp
(defun C:SEQRAND (/ rand currnt ptlst) |
|
(setvar "cmdecho" 0) |
;no echo to prompt |
(setq rand T) |
;set up rand |
(setq currnt (getint "\nEnter first number in sequence: ")) |
|
(while rand |
;while point is picked |
(setq rand (getpoint "\nSelect points in sequence: " ));get point |
|
(setq ptlst (append ptlst (list rand) )) |
;add point to list |
) |
|
(mapcar |
|
'(lambda (rand) |
;define lambda expression |
(if rand |
;if point (rand) exists |
(progn |
|
(command "text" rand "" "" currnt) |
;place number at point rand |
(setq currnt (1+ currnt)) |
;get next number |
) |
|
) |
|
) |
|
ptlst |
;list supplied to lambda |
) |
|
(setvar "cmdecho" 1) |
;echo to prompt on |
(princ) |
|
) |
|
|
|
Figure 9.2: Program to place sequential number in random locations
189
Copyright © 2001 George Omura,,World rights reserved
The ABC’s of AutoLISP by George Omura
In the C:SEQRAND program, the following while expression is used to allow the user to pick random point locations for the numbered sequence:
(while (not (not rand))
(setq rand (getpoint "\nSelect points in sequence: " ))
(setq ptlst (append ptlst (list rand) ))
)
This while expression creates the list ptlst comprised of points entered by the user. The user see the prompt:
Select points in sequence:
each time he or she selects a point. Once the user is done, the mapcar expression reads the list of points and applies them to a function that enters the sequence of numbers at those points:
(mapcar '(lambda (rand) (if (not (not rand)) (progn
(command "text" rand "" "" currnt) (setq currnt (1+ currnt))
)
)
)
ptlst
)
In this set of expressions, mapcar applies the elements of the list ptlst to a lambda expression. You may recall that a lambda expression is like a function created using defun. The difference being that lambda expressions have no name. The lambda expression above uses the single argument rand and, using the AutoCAD text command, writes the variable currnt to the drawing using rand as a coordinate to place the text. The lambda expression also adds 1 to the currnt variable increasing the number being added to the drawing by 1.
190
Copyright © 2001 George Omura,,World rights reserved