码迷,mamicode.com
首页 > 其他好文 > 详细

1 Two Sum

时间:2015-11-05 22:15:12      阅读:254      评论:0      收藏:0      [点我收藏+]

标签:

1 Two Sum

Given an array of integers, find two numbers such that they add up to a specific target number.

The function twoSum should return indices of the two numbers such that they add up to the target, where index1 must be less than index2. Please note that your returned answers (both index1 and index2) are not zero-based.

You may assume that each input would have exactly one solution.
Input: numbers={2, 7, 11, 15}, target=9
Output: index1=1, index2=2

解题思路:
最直接最暴力的方法当然是穷举,直到找到合适的解。然而这样复杂度太高,直接就运行超时了。
测试集里包含负数以及相同的数(比如,target=0,输入中有两个0,0+0=0),增大了程序的难度。
为了降低复杂度,首先缩小数据集是最重要的,将x+min(numbers)>target的和x+max(numbers)<target的数据都删掉,这样能很大程度上缩小数据范围。

  1. class Solution(object):
  2. def twoSum(self, nums, target):
  3. """
  4. :type nums: List[int]
  5. :type target: int
  6. :rtype: List[int]
  7. """
  8. d=zip(range(1,len(nums)+1),nums)
  9. d1=sorted(d,key=lambda dn : dn[1])
  10. d1=zip(*d1)
  11. dmin=target-min(d1[1])
  12. dmax=target-max(d1[1])
  13. select= [(x<=dmin and x>=dmax) for x in d1[1]]
  14. select2=[]
  15. for i in range(len(nums)):
  16. if(select[i]==True):
  17. select2.append(i)
  18. slen=len(select2)
  19. for i in range(slen):
  20. rlist=range(i+1,slen)
  21. rlist.reverse()
  22. for j in rlist:
  23. if d1[1][select2[i]]+d1[1][select2[j]]==target:
  24. return sorted([d1[0][select2[i]],d1[0][select2[j]]])
  25. elif d1[1][i]+d1[1][j]<target:
  26. break
  27. return None

写这个程序,发现几个Python中非常棒的函数,首先zip可以将多个list合并成高维list,zip(*list)可以用来矩阵转置。
对多维数组排序,可以选定排序的key值 d1=sorted(d,key=lambda dn : dn[1])

下面看看论坛中大神如何用Python快速实现,而且还比我这个运行速度快多了(T。T我这个思想可能用C代码会快很多,高级语言在直接读取数组上速度都很慢的说)

  1. class Solution:
  2. # @return a tuple, (index1, index2)
  3. # 8:42
  4. def twoSum(self, num, target):
  5. map = {}
  6. for i in range(len(nums)):
  7. if nums[i] not in map:
  8. map[target - nums[i]] = i + 1
  9. else:
  10. return map[nums[i]], i + 1
  11. return -1, -1

这个程序的思路是,依次读如数据,把target-num的值作为key,该num的index作为字典的value。后面的只用查字典,如果不在字典里,则加进字典;如果在,就找到正确答案了。速度快很多56ms,我的是80ms
更简练的写法:

  1. def twoSum(self, nums, target):
  2. """
  3. :type nums: List[int]
  4. :type target: int
  5. :rtype: List[int]
  6. """
  7. d={}
  8. for i, n in enumerate(nums):
  9. if d.has_key(n):
  10. return (d[n]+1, i+1)
  11. else:
  12. d[target-n]=i
  13. return (0,0)

enumerate可以生成这样的序列: (0, seq[0]), (1, seq[1]), (2, seq[2]), ...

再换一种写法:

  1. class Solution:
  2. # @param {integer[]} nums
  3. # @param {integer} target
  4. # @return {integer[]}
  5. def twoSum(self, nums, target):
  6. scanned = {}
  7. for j, item in enumerate(nums, 1):
  8. i = scanned.get(target - item, -1)
  9. if i > 0:
  10. return [i, j]
  11. scanned[item] = j

这里dict.get函数,跟has_key功能类似

D.get(k[,d]) -> D[k] if k in D, else d. d defaults to None.

看看人家写的真长姿势。





1 Two Sum

标签:

原文地址:http://www.cnblogs.com/miclita/p/4940763.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!