最简单的方法是先将数组排序,然后找中位数。但此种方法肯定不是最优的。一个比较好的做法是利用小顶堆。思路如下:
1.取前len(nums)//2个元素建立小顶堆。可以知道堆顶元素是前len(nums)/2个元素中最小的。
2.从第len(nums)//2+1个元素开始,依次将其与堆顶元素比较。若比对顶元素大,则替换之,并调整堆。
3.数组剩下的所有元素比较完后,可以输出中位数。数组长度为奇数时,输出堆顶元素即可。数组长度为偶数时,输出堆顶元素与它的孩子结点中较小的那个的均值。
代码如下:
#coding:utf-8
def heap_adjust(parent,heap): #更新结点后进行调整
child=2*parent+1
while len(heap)>child:
if child+1<len(heap):
if heap[child+1]<heap[child]:
child+=1
if heap[parent]<=heap[child]:
break
heap[parent],heap[child]=heap[child],heap[parent]
parent,child=child,child*2+1
def find(nums):
heapnum=len(nums)//2
heap=nums[:heapnum+1]
for i in range(len(heap)//2-1,-1,-1): #前n/2个元素建堆
heap_adjust(i,heap)
for j in range(heapnum+1,len(nums)):
if nums[j]>heap[0]:
heap[0]=nums[j]
heap_adjust(0,heap)
#奇数时是最中间的数,偶数时是最中间两数的均值
return heap[0] if len(nums)%2==1 else float(heap[0]+min(heap[1],heap[2]))/2