常见的Lisp:KEY参数使用 [英] Common lisp :KEY parameter use

查看:87
本文介绍了常见的Lisp:KEY参数使用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Common Lisp附带的某些功能中包含:KEY参数.我发现的所有描述都无济于事,并且:KEY很难在搜索引擎中进行搜索,因为通常会忽略:".

The :KEY parameter is included in some functions that ship with Common Lisp. All of the descriptions that I have found of them are unhelpful, and :KEY is difficult to search in a search engine because the ":" is usually ignored.

例如,如何在允许同时使用:TEST:KEYmember函数中使用它?

How would it be used, for example, in the member function which allows both :TEST and :KEY?

推荐答案

想象一下我们有一个城市列表:

Imagine that we have a list of cities:

(defparameter *cities*
   ; City       Population  Area km^2
  '((Paris      2265886     105.4)
    (Mislata    43756       2.06)
    (Macau      643100      30.3)
    (Kallithea  100050      4.75)
    (Nea-Smyrni 73090       3.52)
    (Howrah     1072161     51.74)))

现在我们可以计算人口密度,单位为人/km ^ 2

Now we can compute the population density in people/km^2

(defun city-density (city)
  "the density is the population number divided by the area"
  (/ (second city) (third city)))

现在,我们要计算人口密度低于21000人/公里^ 2的所有城市的列表.

Now we want to compute a list of all cities which have a density less than 21000 people/km^2.

我们从列表中删除了所有较大的文件,并提供了:test-not函数.我们需要提供一个匿名函数来进行测试并计算要比较的城市的密度.

We remove all larger ones from the list and are providing a :test-not function. We need to provide an anonymous function which does the test and computes the density of the city to compare.

CL-USER 85 > (remove 21000 *cities*
                     :test-not (lambda (a b)
                                 (>= a (city-density b))))

((NEA-SMYRNI 73090 3.52) (HOWRAH 1072161 51.74))

我们可以通过提供数字:test-not函数>=并使用city-density函数作为键来计算每个提供的城市的价值,从而简化不使用匿名函数的情况:

We can write it simpler without the anonymous function by providing the numeric :test-not function >= and use the city-density function as the key to compute the value from each provided cities:

CL-USER 86 > (remove 21000 *cities* :test-not #'>= :key #'city-density)

((NEA-SMYRNI 73090 3.52) (HOWRAH 1072161 51.74))

因此,既具有测试谓词又具有键函数,可以更轻松地提供用于序列计算的构件...

So having both a test predicate and a key function makes it easier to provide the building blocks for sequence computations...

现在想象我们使用CLOS和城市CLOS对象的列表:

Now imagine that we use CLOS and a list of city CLOS objects:

(defclass city ()
  ((name :initarg :name :reader city-name)
   (population :initarg :population :reader city-population)
   (area :initarg :area :reader city-area)))

(defparameter *city-objects*
  (loop for (name population area) in *cities*
        collect (make-instance 'city
                               :name name
                               :population population
                               :area area)))

(defmethod density ((c city))
  (with-slots (population area)
      c
    (/ population area)))

现在,我们按上述方式计算列表:

Now we compute the list as above:

CL-USER 100 > (remove 21000 *city-objects* :test-not #'>= :key #'density)
(#<CITY 42D020DDFB> #<CITY 42D020DF23>)

CL-USER 101 > (mapcar #'city-name *)
(NEA-SMYRNI HOWRAH)

如果我们将密度作为带有吸气剂的插槽,则可以执行以下操作:

If we have the density as a slot with a getter, we can do this:

(defclass city ()
  ((name :initarg :name :reader city-name)
   (population :initarg :population :reader city-population)
   (area :initarg :area :reader city-area)
   (density :reader city-density)))

(defmethod initialize-instance :after ((c city) &key)
  (with-slots (density)
      c
    (setf density (density c))))

(defparameter *city-objects*
  (loop for (name population area) in *cities*
        collect (make-instance 'city
                               :name name
                               :population population
                               :area area)))

现在我们按上述方法计算列表,但是 key density 插槽的吸气剂:

Now we compute the list as above, but the key is the getter of the density slot:

CL-USER 102 > (remove 21000 *city-objects* :test-not #'>= :key #'city-density)
(#<CITY 42D026D7EB> #<CITY 42D026D913>)

CL-USER 103 > (mapcar #'city-name *)
(NEA-SMYRNI HOWRAH)

这篇关于常见的Lisp:KEY参数使用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆