2017-06-20 85 views
3

我把一个假问题,来说明我的观点:说我们有以下几种实用的功能,以显示有关特定排序算法的信息:是否有可能使用高阶函数与可选参数

fun sort(name: String, array: Array<Int>, sortingAlgorithm: (Array<Int>) -> Array<Int>) { 
    println(name) 
    sortingAlgorithm(array).forEach { print(" $it ") } 
    println() 
} 

你会使用这样的:

sort("Selection Sort - Θ(n^2)", arrayOf(2, 3, 1), ::selectionSort) 

而且这个工程,因为selectionSort签名很简单:fun selectionSort(array: Array<Int>): Array<Int> {

但说我有以下签名

fun quickSort(array: Array<Int>, 
       start: Int = 0, 
       end: Int = array.size - 1): Array<Int> { 

最后两个参数是可选的另一种排序算法,所以理论上你可以调用quickSort你叫selectionSort以同样的方式。也就是说,它尊重签名(Array<Int>) -> Array<Int>对吗?

不幸的是,当我尝试打电话sort("Quick Sort", arrayOf(2, 3, 1), ::quickSort)我得到:

type missmatch

我觉得编译器不是明智地意识到,这两个参数都是可选的。如何避免这个问题,除了重载sort方法来接受带签名的高阶函数?

+1

难道你不能只使用lambda表达式而不是方法引用? –

+0

你的意思是这样的:sort(“Quick Sort”,{quickSort(unsorted)}),yes,that works!但我只是想知道为什么其他方式不行。它觉得它应该可以工作。 – feresr

+0

大拇指寻找这样不切实际的问题:D – voddan

回答

3

没有避免这种问题,因为它会抵触科特林类型的系统2个基石:

  • 1)每个表达具有类型(强类型)
  • 2)的接收器侧不会影响表达式的类型(本地推断)

例如,如果你能做到这一点,以下将无法正常工作,这就是你们的榜样的一个简单的重构:

val algorithm = ::quickSort 
sort("Quick Sort", arrayOf(2, 3, 1), algorithm) 

无论如何,sort("Quick Sort", { quickSort(unsorted) })解决方法对于Kotlin开发人员来说花费时间在这个问题上太简单了。

相关问题