如何将自定义ab函数整合进快速排序,实现Int数对按差值绝对值升序排序?
按数对差值绝对值升序排序的解决方案
我来帮你搞定这个问题~你现在的核心困扰是原来的快速排序函数用的是Haskell默认的元组比较逻辑,而你需要换成基于ab函数计算的差值绝对值来做排序依据,对吧?
首先先帮你简化下ab函数,其实Haskell标准库已经有计算绝对值的abs函数啦,你的ab可以直接写成:
ab :: (Int, Int) -> Int ab (x, y) = abs (x - y)
这样和你原来的逻辑完全一样,但更简洁易读。
接下来看你的快速排序函数,问题出在smallerOrEqual和larger的判断条件上:原来的a <= x是直接比较(Int,Int)元组的默认顺序(先比第一个元素,再比第二个),这不是你要的。我们只需要把比较逻辑换成比较两个数对通过ab计算出的差值绝对值就行:
-- 改名成sortByDiff避免和标准库的sort重名 sortByDiff :: [(Int,Int)] -> [(Int,Int)] sortByDiff [] = [] sortByDiff (x:xs) = sortByDiff smallerOrEqual ++ [x] ++ sortByDiff larger where -- 现在判断的是a的差值绝对值 <= x的差值绝对值 smallerOrEqual = [a | a <- xs, ab a <= ab x] -- 同理,判断a的差值绝对值 > x的差值绝对值 larger = [a | a <- xs, ab a > ab x]
测试一下这个函数,比如输入sortByDiff [(3,1), (5,9), (2,2)],会得到[(2,2), (3,1), (5,9)],完全符合按差值绝对值升序的要求(它们的差值绝对值分别是0、2、4)。
如果你不想自己实现快速排序,Haskell标准库其实提供了更简洁的方案,用sortBy和comparing函数:
import Data.Ord (comparing) import Data.List (sortBy) sortByDiff :: [(Int, Int)] -> [(Int, Int)] sortByDiff = sortBy (comparing ab)
comparing ab会生成一个比较函数,专门用来比较两个元素的ab计算结果,sortBy用这个函数来完成排序,既高效又不用重复造轮子~
不管是自己写排序还是用标准库,核心思路都是把排序的比较依据从数对本身,换成数对通过ab得到的差值绝对值,这样就能实现你想要的排序效果啦。
内容的提问来源于stack exchange,提问作者CoreNoob
相关产品推荐
相关产品推荐

