Common lisp Lisp自定义比较函数

Common lisp Lisp自定义比较函数,common-lisp,Common Lisp,假设我定义了一个新类foo: (defclass foo () ((bar :initarg :bar ...) (baz :initarg :baz ...) ...)) 我想为foo创建一个自定义比较器,例如: (defun foo-equalp (foo1 foo2) (equalp (bar foo1))) 是否有更好、更明确的方法将此foo equalp函数与foo类联系起来 我想不必将#'foo-equalp作为:test参数传递给像REMOVE-DUPLIC

假设我定义了一个新类
foo

(defclass foo ()
  ((bar :initarg :bar ...)
   (baz :initarg :baz ...)
   ...))
我想为
foo
创建一个自定义比较器,例如:

(defun foo-equalp (foo1 foo2)
  (equalp (bar foo1)))
是否有更好、更明确的方法将此
foo equalp
函数与
foo
类联系起来


我想不必将
#'foo-equalp
作为
:test
参数传递给像
REMOVE-DUPLICATES
这样的函数,但即使这不可能,我还是想知道是否有一种更惯用的Lisp方法来定义这个函数。

如果我理解你的问题,我可以在这里提供帮助

(defgeneric foo-equalp (foo1 foo2))

(defmethod foo-equalp ((foo1 foo) (foo2 foo))
  (and (equal (bar foo1) (bar foo2))
       (equal (baz foo1) (baz foo2))))
现在,当您使用非foo类型的对象调用foo equalp时,会出现此错误

There is no applicable method for the generic function
  #<STANDARD-GENERIC-FUNCTION FOO-EQUALP (1)>
when called with arguments
  (1 2).
在这里,我们专门经营。调用方法时,common lisp将始终为参数选择“最接近/最具体”的类型匹配(这是一个非常糟糕的描述。我需要更多咖啡,请查看链接,因为它非常棒:)

  • 您实际上不需要专门化t,因为这是默认值,但我想包含它以显示发生了什么

下面是实用的公共Lisp(链接在本文顶部)的片段 (答复)

泛型函数定义抽象操作,并指定其名称 和参数列表,但没有实现。实际执行情况 泛型函数的类型由方法提供

方法指示它们可以处理哪些类型的参数 专门化泛型函数定义的所需参数

例如,对于泛型函数draw,可以定义一个方法 它专门用于作为对象实例的对象的形状参数 类是圆形的,而另一个方法专门处理对象的形状 这是类三角形的实例


如果我理解你的问题,那么我可以在这里提供帮助

(defgeneric foo-equalp (foo1 foo2))

(defmethod foo-equalp ((foo1 foo) (foo2 foo))
  (and (equal (bar foo1) (bar foo2))
       (equal (baz foo1) (baz foo2))))
现在,当您使用非foo类型的对象调用foo equalp时,会出现此错误

There is no applicable method for the generic function
  #<STANDARD-GENERIC-FUNCTION FOO-EQUALP (1)>
when called with arguments
  (1 2).
在这里,我们专门经营。调用方法时,common lisp将始终为参数选择“最接近/最具体”的类型匹配(这是一个非常糟糕的描述。我需要更多咖啡,请查看链接,因为它非常棒:)

  • 您实际上不需要专门化t,因为这是默认值,但我想包含它以显示发生了什么

下面是实用的公共Lisp(链接在本文顶部)的片段 (答复)

泛型函数定义抽象操作,并指定其名称 和参数列表,但没有实现。实际执行情况 泛型函数的类型由方法提供

方法指示它们可以处理哪些类型的参数 专门化泛型函数定义的所需参数

例如,对于泛型函数draw,可以定义一个方法 它专门用于作为对象实例的对象的形状参数 类是圆形的,而另一个方法专门处理对象的形状 这是类三角形的实例


如果我理解你的问题,那么我可以在这里提供帮助

(defgeneric foo-equalp (foo1 foo2))

(defmethod foo-equalp ((foo1 foo) (foo2 foo))
  (and (equal (bar foo1) (bar foo2))
       (equal (baz foo1) (baz foo2))))
现在,当您使用非foo类型的对象调用foo equalp时,会出现此错误

There is no applicable method for the generic function
  #<STANDARD-GENERIC-FUNCTION FOO-EQUALP (1)>
when called with arguments
  (1 2).
在这里,我们专门经营。调用方法时,common lisp将始终为参数选择“最接近/最具体”的类型匹配(这是一个非常糟糕的描述。我需要更多咖啡,请查看链接,因为它非常棒:)

  • 您实际上不需要专门化t,因为这是默认值,但我想包含它以显示发生了什么

下面是实用的公共Lisp(链接在本文顶部)的片段 (答复)

泛型函数定义抽象操作,并指定其名称 和参数列表,但没有实现。实际执行情况 泛型函数的类型由方法提供

方法指示它们可以处理哪些类型的参数 专门化泛型函数定义的所需参数

例如,对于泛型函数draw,可以定义一个方法 它专门用于作为对象实例的对象的形状参数 类是圆形的,而另一个方法专门处理对象的形状 这是类三角形的实例


如果我理解你的问题,那么我可以在这里提供帮助

(defgeneric foo-equalp (foo1 foo2))

(defmethod foo-equalp ((foo1 foo) (foo2 foo))
  (and (equal (bar foo1) (bar foo2))
       (equal (baz foo1) (baz foo2))))
现在,当您使用非foo类型的对象调用foo equalp时,会出现此错误

There is no applicable method for the generic function
  #<STANDARD-GENERIC-FUNCTION FOO-EQUALP (1)>
when called with arguments
  (1 2).
在这里,我们专门经营。调用方法时,common lisp将始终为参数选择“最接近/最具体”的类型匹配(这是一个非常糟糕的描述。我需要更多咖啡,请查看链接,因为它非常棒:)

  • 您实际上不需要专门化t,因为这是默认值,但我想包含它以显示发生了什么

下面是实用的公共Lisp(链接在本文顶部)的片段 (答复)

泛型函数定义抽象操作,并指定其名称 和参数列表,但没有实现。实际执行情况 泛型函数的类型由方法提供

方法指示它们可以处理哪些类型的参数 专门化泛型函数定义的所需参数

例如,对于泛型函数draw,可以定义一个方法 它专门用于作为对象实例的对象的形状参数 类是圆形的,而另一个方法专门处理对象的形状 这是类三角形的实例


听起来您需要一个等式谓词,它是一个可以添加专门方法的通用函数(有点像在Java中专门化
.equals()
)。不幸的是,没有一个“公共”谓词(
eq
eql