The Apostrophe and the Quote Function ‘和引用函数 未翻译完)

copyright :http://lee-mac.com/quote.html

The Apostrophe (单引号)

The apostrophe or single-quote character marks an expression or symbol as a literal expression(Returns an expression without evaluating it), to be taken at 'face-value' and not to be evaluated by the AutoLISP interpreter.

The quoted expression may be any form of AutoLISP data, though the apostrophe is usually used with lists or symbols, since most other forms of AutoLISP data (strings, integers, reals) are already literal constants and hence do not require its use.

 

Constant Data 常量

 

Expressions that contain constant or fixed data (that is, data that is unchanged when evaluated) may be quoted as literal expressions, as there are no symbols within the expression to be evaluated and consequently change the data content.

一般来说,常数或者固定数据的表达式可以被引用为quote表达式,而且表达式中没有变量需要求值而改变数据内容。

The quoted expression may be any form of AutoLISP data, though the apostrophe is usually used with lists or symbols, since most other forms of AutoLISP data (strings, integers, reals) are already literal constants and hence do not require its use.

 

 

_$ (list 1 2 3 4 5)
(1 2 3 4 5)
_$ '(1 2 3 4 5)
(1 2 3 4 5)

 

 

_$ (list (cons 1 "a") (cons 2 "b") (cons 3 "c"))
((1 . "a") (2 . "b") (3 . "c"))

 

_$ '((1 . "a") (2 . "b") (3 . "c"))
((1 . "a") (2 . "b") (3 . "c"))

To offer a practical example, consider the list of dotted pairs which may be supplied to the ssget function as the filter list argument.

The following example will retrieve a selection set of all Closed LWPolyline objects in the drawing database:

(ssget "_X" '((0 . "LWPOLYLINE") (-4 . "&=") (70 . 1)))

Since the above filter list contains only constant data, the list may be quoted as a literal expression using the apostrophe.

 

 

ariable Data(变量)

_$ (setq x 5)
5
_$ (list 1 2 3 4 x)
(1 2 3 4 5)

 

_$ (setq x 5)
5
_$ '(1 2 3 4 x)
(1 2 3 4 X)
;;由于x是变量,如果使用引用得不得变量的值,只是得到变量的符号。
(if (snvalid (setq lay (getstring t "\nSpecify layer: ")))
    (ssget "_X" (list '(0 . "LWPOLYLINE") '(-4 . "&=") '(70 . 1) (cons 8 lay)))
)
;;同样lay是变量,如果要得到它的值,需要使用list函数,而不是quote。

 

Function Arguments 函数参数

_$ (mapcar '+ '(1 2 3 4 5) '(6 7 8 9 10))
(7 9 11 13 15)

Here, the apostrophe is used to mark the + function as an argument for the mapcar function, with the two list arguments also quoted since they contain constant data.

 

Consider that if this function argument were not quoted, the function symbol would be evaluated by the mapcar function to yield the pointer to its function definition, and the mapcar function would consequently return a 'bad function' error.

假设这个函数参数没有被引用,+函数会被mapcar 函数执行来得到指向其函数定义指针,这样mapcar 就会返回a 'bad function' error。

The same logic applies when supplying an anonymous lambda function as the functional argument to be evaluated by mapcar on every item in the given list(s), as demonstrated by the following example calculating the midpoint between two points:

$ (mapcar '(lambda ( a b ) (/ (+ a b) 2.0)) '(12.3 45.6 78.9) '(32.1 65.4 98.7))
(22.2 55.5 88.8)
;;原理同上。

To offer another example, consider the following getvar expression:

_$ (getvar 'osmode)
255

Here, the symbol osmode is quoted to ensure that the symbol is not evaluated when passed as an argument to the getvar function. Since both the getvar & setvar functions accept either a string or symbol argument, this expression will then return the value of the OSMODE system variable, as demonstrated above.

Consider that if the symbol argument was not quoted, the getvar function would evaluate the argument to yield any value that has been assigned to the symbol in the active document namespace (e.g. via a setq or set expression); if the symbol holds no value (or indeed, holds a value other than a valid string or symbol argument), the getvar expression would consequently error with a 'bad argument type: (or stringp symbolp)' error.

Finally, observe the following expression which invokes the Visual LISP ActiveX getboundingbox method (for example, as used by my Bounding Box & Selection Set Bounding Box functions):

(if (setq ent (car (entsel)))
    (vla-getboundingbox (vlax-ename->vla-object ent) 'pt1 'pt2)
)

The getboundingbox method requires three parameters: the VLA-Object whose bounding box is to be calculated, and two symbol parameters to hold the values output by the method.

The utilisation of output parameters enables the method to return multiple values, as opposed to the single value returned following function evaluation (which happens to be nil for this method).

 

 

When invoking the method, the symbol parameters are quoted to ensure that the symbol itself is supplied as an argument to the method, rather than the value obtained when such symbol is evaluated. Following successful evaluation of the method, the supplied symbols are assigned the lower-left & upper-right WCS coordinates describing the bounding box of the supplied VLA-Object.

 

The Quote Function

The quoted expression may be any form of AutoLISP data, though the apostrophe is usually used with lists or symbols, since most other forms of AutoLISP data (strings, integers, reals) are already literal constants and hence do not require its use.

(????未翻译。。。)

Constant Data

_$ (quote (1 2 3 4 5))
(1 2 3 4 5)

Similarly, the mapcar expressions from our previous examples could also be rewritten using the quote function in place of the apostrophe:

_$ (mapcar (quote +) (quote (1 2 3 4 5)) (quote (6 7 8 9 10)))
(7 9 11 13 15)

 

However, where the second mapcar example is concerned, the lambda function may be optimised when the code is compiled to a VLX or FAS file by substituting the function function in place of the apostrophe or quote function:

(使用function定义的lambda匿名函数在编译时候可以被优化(使用function替换原来引用function的位置)。

_$ (mapcar (function (lambda ( a b ) (/ (+ a b) 2.0))) (quote (12.3 45.6 78.9)) (quote (32.1 65.4 98.7)))
(22.2 55.5 88.8)

 

The function function is identical to the quote function with the exception that it instructs the Visual LISP compiler that the enclosed symbol or lambda expression is a function argument which may be linked & optimised during compilation.
Since lambda expressions are defined at run-time, the Visual LISP compiler cannot optimise these expressions during compilation, as is possible with built-in AutoLISP functions or named functions defined with defun. Similarly, when quoted using the apostrophe or quote function, the compiler treats the quoted lambda expression simply as literal data, without linking or optimising the function.
However, by using function, the compiler is instructed to optimise the lambda function during compilation to yield similar performance to built-in or named functions during evaluation.
The function function can also be used with symbols defining any built-in or named function, however, since these functions are already optimised when compiled, there is very little gain in performance, if any.

未翻译。。。。。。。。。。。。。。)

 

Run-time Evaluation 运行时求值

Since the quote function operates in an identical manner to the apostrophe, it may appear that this function is redundant since apparently the apostrophe could be used in its place with far fewer keystrokes.

However, there are situations in which the quote function must be used in place of the apostrophe to obtain the desired result.

One such example is literal expressions that are defined at run-time. (another is quines...)

Consider the following simplified example:

_$ (eval (list 'defun-q 'fun '( / lst ) (list 'setq 'lst (list 'quote (list 0.0 (* pi 0.5) pi (* pi 1.5))))))
FUN

 

 

When evaluated, the above expression will define the function fun which contains a single setq expression assigning a list of four numerical items (multiples of π) to the local variable lst.

I have intentionally defined the above function using a defun-q expression so that the result of the function definition may be revealed when the symbol fun is evaluated:

这里故意使用defun-q是因为这种定义函数的方式,通过在命令行输入 变量名可以得出函数定义的内容。。。(翻译太烂…)

  //另:

(defun-q sym ([arguments] [/ variables...]) expr...)

将函数定义为表

defun-q 函数是仅仅出于与早期版本 AutoLISP 的兼容性考虑而设置的,不能用作其他用途。在需要访问定义为表结构的函数时,可以使用 defun-q。这种使用方式与早期非编译 AutoLISP 版本中 defun 的实现方式一致。

_$ fun
((/ LST) (SETQ LST (QUOTE (0.0 1.5708 3.14159 4.71239))))

Following definition of the function, observe that the setq expression is now assigning a literal list to the symbol lst, without repeated calculation of the list items, and more importantly, without any loss of precision of each item (the displayed values are truncated when displayed at the console for ease of viewing, however, these values are still stored to the maximum level of precision available).

根据这种定义函数方式 , setq 表达式被分配了一个a literal list(字面上的表 <翻译太差>给这个变量表,而没有重复对这个表中的子项求值更重要的是没有造成精度丢失   (控制台中为了显示数值方便被截断了。但是真实值仍然以最高级的精度存储着。)

//这种定义方式与下面的方式的区别在于,这种方式仅在第一次调用时候进行计算,fun变量被赋值为  ((/ LST) (SETQ LST (QUOTE (0.0 1.5708 3.14159 4.71239)))) 。

Consider that in order to obtain the same result using a quoted literal list, each irrational multiple of π would need to be expressed in the code to around 15 decimal places to achieve the same precision.

Alternatively, the function could be defined such that the arithmetic expressions are included in the function definition:

_$ (defun-q fun ( / lst ) (setq lst (list 0.0 (* pi 0.5) pi (* pi 1.5))))
FUN

_$ fun
((/ LST) (SETQ LST (LIST 0.0 (* PI 0.5) PI (* PI 1.5))))

However, with the function defined in this way, the multiples of π are calculated and re-calculated unnecessarily every time the function is evaluated, introducing inefficiency.

然而用这种方式定义函数,多个π表达式每次调用都会被计算或者重复计算,这是不必要的,这造成函数评估效率低下。

For the above example, this loss in performance is of course negligible and one must also consider the negative effect on the readability of the code when opting to define the function at run-time; however, if the list were to contain potentially thousands of entries, the repeated calculation would soon become noticeable.

通过上面的例子,这种在性能方面的损失时可以忽略的,程序员也必须考虑 “运行时定义函数”的方法造成程序可读性变差的缺点。

然而,如果表中包含数以万记的数据,这种重复计算所带来的开销是显而易见的。

 

Hence, this construct allows large literal lists which could be unmanageable to include directly in the program source code to be constructed at run-time whilst simultaneously retaining accuracy and improving efficiency.

因此,这种结构使得正常情况下在代码中不易直接操控的大量“字面”的表能够被构造成一种“运行时计算的结构”,同时保证精度和提高效率。

 

To offer a concrete example of the quote function being used in this manner, consider my GrText function. The quoted vector list which appears at the top of this function definition is already quite large, but without the use of the run-time redefinition, the literal list would be twice as large!

 

 

 

Function References

Below are links to the formal documentation for the various functions described above.
As far as I am aware, there is no formal documentation for the apostrophe.

Quote Reference

Function Reference

原文地址:https://www.cnblogs.com/InspiringMind/p/3878278.html