和为S的两个数字
时间限制:1秒 空间限制:32768K 热度指数:193376
算法知识视频讲解
题目描述
输入一个递增排序的数组和一个数字S,在数组中查找两个数,使得他们的和正好是S,如果有多对数字的和等于S,输出两个数的乘积最小的。
输出描述:
对应每个测试案例,输出两个数,小的先输出。
解析
这里需要证明一个式子:
输出两个数的乘积最小的。这句话的理解?
假设:若b>a,且存在,
a + b = s;
(a - m ) + (b + m) = s
则:(a - m )(b + m)=ab - (b-a)m - m*m < ab;说明外层的乘积更小
代码:1.暴力法
# -*- coding:utf-8 -*-
class Solution:
def FindNumbersWithSum(self, array, tsum):
# write code here
for i in array:
if tsum - i in array:
if tsum - i == i: # 这里判断是不是tsum是某个数的二倍
if array.count(i) > 1:
return [i, i]
else:
return [i, tsum - i] # 由与已经证明多组和相同的两个数相乘,最小和最大的两个数乘积最小
return []
代码:2.双指针
class Solution:
def FindNumbersWithSum(self, array, tsum):
if len(array) == 0:
return []
small, big = 0, len(array) - 1
while small < big:
if array[small] + array[big] == tsum:
return [array[small], array[big]]
elif array[small] + array[big] > tsum:
big -= 1
else:
small += 1
return []
链接:https://www.nowcoder.com/questionTerminal/390da4f7a00f44bea7c2f3d19491311b
来源:牛客网
update:2019年10月8日
二分查找
# -*- coding:utf-8 -*-
class Solution:
def FindNumbersWithSum(self, array, tsum):
# write code here
for i in range(len(array)):
j = self.binary_search(array, tsum-array[i])
if j != -1 and j != i:
if array[i] < array[j]:
return array[i], array[j]
else:
return array[j], array[i]
return []
def binary_search(self, data, k):
l, r = 0, len(data) - 1
while l <= r:
mid = (l+r)//2
item = data[mid]
if k > item:
l = mid + 1
elif k < item:
r = mid - 1
elif item == k:
return mid
return -1