Jump to content

Association Lists


samifox

Recommended Posts

Hi

My code does the following

 

  1. ask user for point a , b
  2. ask user for lines a b c d
  3. return an association list containing all user input

i watch the veritable userData, i get 20 items while expecting to have 7.

 

can someone explain why?

 

(defun main()
 (setq userData (wl:getUserData))
 )

(defun wl:getUserData (/ strpt endpt)
 (if (setq strpt (getpoint "\nStart point of path: "))
   (if    (setq endpt (getpoint strpt "\nEndpoint of path: "))
   (progn
     (setq wall (getPoly wall "\nSelect Wall eleveation line"))
     (setq front (getPoly front "\nSelect Front eleveation line"))
     (setq back (getPoly back "\nSelect Back eleveation line"))
     (setq exist (getPoly exist "\nSelect Exist eleveation line"))
     (list
      cons 10 strpt
      cons 11 endpt
      cons 41 (distance strpt endpt)
      cons 51 wall
      cons 52 front
      cons 53 back
      cons 54 exist
     ) ;_list
       
     );_progn
   ) ;_if endpt
 ) ;_if strp
) ;_defun


(defun getPoly (ent msg)
(if (setq ent (car (entsel msg)))
   (if    (eq (cdr (assoc 0 (entget ent))) "LWPOLYLINE")
   (princ)
   ) ;_if
 ) ;_if
 ent
)

 

Thanks

Shay

Link to comment
Share on other sites

i watch the veritable userData, i get 20 items while expecting to have 7.

 

Your wl:getUserData function will return a list of 21 items because you are supplying the list function with 21 arguments from which to construct the list:

(list cons 10 strpt cons 11 endpt cons 41 (distance strpt endpt) cons 51 wall cons 52 front cons 53 back cons 54 exist)

It seems that you are missing several expressions:

(list
   (cons 10 strpt)
   (cons 11 endpt)
   (cons 41 (distance strpt endpt))
   (cons 51 wall)
   (cons 52 front)
   (cons 53 back)
   (cons 54 exist)
)

Note also that your getPoly function will return an entity name whether or not the user selects an LWPolyline or any other object:

(defun getPoly ( ent msg )
   (if (setq ent (car (entsel msg)))
       (if (eq (cdr (assoc 0 (entget ent))) "LWPOLYLINE")
           (princ)
       )
   )
   ent
)

The ent argument for this function is also redundant since it is immediately redefined as a local variable.

 

Also, note that your various 'getPoly' expressions will return nil if the user fails to select an object, resulting in the variables wall, front, back, exist holding null values.

(setq wall (getPoly wall "\nSelect Wall eleveation line"))

Link to comment
Share on other sites

i see

 

is there a point to include parameters in the function (define fun(/v1 v2) and than define again inside the function (setq v1 2) (setq v2 2) ?

 

Thanks

Shay

Link to comment
Share on other sites

is there a point to include parameters in the function (define fun (/ v1 v2) and than define again inside the function (setq v1 2) (setq v2 2)?

 

Symbols following the forward slash within the defun expression are variables whose scope is local to the function being defined, these are not arguments or parameters required by the function. Symbols defined within the function but not declared as local variables within the defun expression will be global (unless declared local to a calling function).

Link to comment
Share on other sites

i thought what makes variables global or local is their position in the code (outside or inside the function).

so you say defun variables are local,

setq variables inside and or outside the function are global

and if both exist so the variables in the defun overrides those defined by setq?

 

Thanks

Shay

Link to comment
Share on other sites

setq variables inside and or outside the function are global

 

No - as stated above, defined symbols which are listed following the forward slash within the defun expression will be local to that function.

 

Consider the following example demonstrating variable scope:

[i][color=green];; Function to print symbol value[/color][/i]
(defun _prin1 ( *sym* )
   (print *sym*)
   (princ "= ")
   (prin1 (eval *sym*))
   (princ)
)

[color=green][i];; Assign global value to symbol var[/i][/color]
(setq var "Global Variable")
(_prin1 'var)

[i][color=green];; Define function-1, var is declared local[/color][/i]
(defun function-1 ( / var )
   (setq var "Value inside function-1.") [i][color=green];; Assign value to symbol var within function-1 definition[/color][/i]
   (_prin1 'var) [i][color=green];; Display assigned value[/color][/i]
   (function-2) [i][color=green];; Evaluate function-2 from within function-1[/color][/i]
   (_prin1 'var) [i][color=green];; Display value of var following evaluation of function-2[/color]
[/i] )

[i][color=green];; Define function-2, var is again declared local[/color][/i]
(defun function-2 ( / var )
   (setq var "Value inside function-2.") [i][color=green];; Assign value to symbol var within function-2 definition[/color][/i]
   (_prin1 'var) [i][color=green];; Display assigned value[/color][/i]
)

(function-1) [color=green][i];; Evaluate function-1[/i][/color]
(_prin1 'var) [i][color=green];; Display value of var following evaluation of function-1[/color][/i]

Result:

VAR = "Global Variable" [color=green];; Assigned global value[/color]
VAR = "Value inside function-1." [color=green];; Value local to function-1[/color]
VAR = "Value inside function-2." [color=green];; Value local to function-2[/color]
VAR = "Value inside function-1." [color=green];; Resume value within function-1[/color]
VAR = "Global Variable" [color=green];; Resume global value[/color]

I suggest you read the Visual LISP IDE (VLIDE) help documentation topics surrounding the defun function and symbol & function handling.

Link to comment
Share on other sites

Note also that your getPoly function will return an entity name whether or not the user selects an LWPolyline or any other object:

 

how can i be kind to the user and instead of quiting the program ill tell him : "This is not a poly, please select a poly"

 

Thanks

Shay

Link to comment
Share on other sites

how can i be kind to the user and instead of quiting the program ill tell him : "This is not a poly, please select a poly"

 

Use a while loop to continuously prompt the user until the selection criteria is met, or the user has dismissed the prompt.

Link to comment
Share on other sites

If your picking 4 plines which I gues is a wall then try this method "pick pt inside" "pick pt outside" using the Fence "F" option you can find all 4 objects in one go if you only have 3 then display message that program will not work

 

(setq pt1 (getpoint "\nPick first point on inside of wall :"))
(setq pt2 (getpoint pt1 "\nPick second point on outside of wall :"))

(setq ss (ssget "F" (list pt1 pt2))) 
(if (< (sslength ss) 4)(Princ "insufficient walls"))

Link to comment
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Unfortunately, your content contains terms that we do not allow. Please edit your content to remove the highlighted words below.
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...