我有文件R
和两个文件A
,B
。
R
始终处于加载状态。
A
xor B
的加载取决于平台特性。我有一个无论在什么平台上都应该存在的函数,调用它F
。
使用的优点/缺点是什么:
DEFGENERIC
在F
中R
,然后DEFMETHOD
在F
中A
,B
DEFUN
'F
A
B
从表面上看,它们应该是一样的。这不仅仅是个人喜好问题吗?
我目前正在采用第一种方法,因为它清楚地表明该函数是通用的并且具有实现,但我很好奇为什么与第二种方法相比它如此重要。
我有文件R
和两个文件A
,B
。
R
始终处于加载状态。
A
xor B
的加载取决于平台特性。我有一个无论在什么平台上都应该存在的函数,调用它F
。
使用的优点/缺点是什么:
DEFGENERIC
在F
中R
,然后DEFMETHOD
在F
中A
,B
DEFUN
'F
A
B
从表面上看,它们应该是一样的。这不仅仅是个人喜好问题吗?
我目前正在采用第一种方法,因为它清楚地表明该函数是通用的并且具有实现,但我很好奇为什么与第二种方法相比它如此重要。
defgeneric
在我看来,在您的情况下使用或的优点或缺点defun
与一般情况没有什么不同,这意味着与通用函数和常规函数之间的通常选择相比,这里没有额外的限制。一般来说,函数更简单,使用起来可能更高效,因为它们的要求较少(没有分派,没有方法组合等),但实践中存在许多优化可以使这种区别变得不那么重要。
A'
如果您有一个几乎相似但经过一些调整的平台A
,通用函数可以为您提供帮助,在这种情况下,您可以专门化一些方法。在您的问题中,您考虑了两种选择,但请注意,您不限于此。例如,请参见Slime如何 定义两个宏
definterface
和defimplementation
,以注册一组必要的后端函数及其在不同平台上的实现。您还可以查看约定调用的各种库,
trivial-*stuff*
这些库将各种特定于实现的代码合并在一起,以便*stuff*
在统一的接口下执行。Common Lisp 中的泛型函数实现了其他面向对象语言中已知的多态性,其中子类型(或其他类型)可以实现或覆盖通用定义的接口或协议。因此从语义上讲,它与普通函数有所不同。
从实际角度来看,从测试的角度来看,cl-mock 只能模拟函数,而不能模拟通用函数。对于这些函数,您必须创建测试类型并为测试中使用的函数进行特定的测试实现。但这可能与您无关。
如果事物在给定图像中只有一个实现,则将其设为函数。如果它可能有多个实现,或者实现可能分布在多个方法上,则将其设为具有方法的通用函数。