Two Sum(hashtable)

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

三种做法:

1.暴力O(n2),找出所有两两数之和,判断是否与target相等,若相等则结束。

2.位置记录,map。由于map的键是自动排序的,所以直接对其进行操作即可

3.参考别人,读完题首先想到的就是两层遍历法,但是显然时间复杂度太高,是O(N^2),不符合要求,于是就应该想如何降低复杂度,首先应该想将逐个比较转变为直接查找,即首先计算出 target与当前元素的差,然后在序列中寻找这个差值,这样首先就把问题简化了,而寻找的过程可以先对序列进行快排,然后二分查找,这样整体的复杂度就降低为 O(N*logN) 了;查找最快的方法是利用一个 map容器存储每个元素的索引,这样取得某个特定元素的索引只需要常数时间即可完成,这样就更快了,最多只需遍历一次序列,将元素及其索引加入map中,在遍历的过程中进行对应差值的查找,如果找到了就结束遍历,这样时间复杂度最多为 O(N)

方法2代码:注意重复的判断,如numbers={0,3,4,0},target=0;由于题目已假设只有一个解决方案,所以若numbers有重复,则重复的这个数,只可能和本身构成target。

class Solution {
public:
    vector<int> twoSum(vector<int> &numbers, int target) {
        int len=numbers.size();
        map<int,int> m;
        vector<int> res;
        for(int i=0;i<len;++i){
            if (!m[numbers[i]])
            {
                m[numbers[i]]=i+1;
            }else
            {
                if(numbers[i]+numbers[i]==target){
                    res.push_back(m[numbers[i]]);
                    res.push_back(i+1);
                    return res;
                }
            }
        }
        map<int,int>::iterator it_beg=m.begin();
        map<int,int>::iterator it_end=m.end();
        --it_end;

        while(it_beg!=m.end()&&it_end!=m.begin()){
            if(it_beg->first+it_end->first>target)
                --it_end;
            else if(it_beg->first+it_end->first<target)
                ++it_beg;
            else{
                res.push_back(it_beg->second);
                res.push_back(it_end->second);
                if(res[0]>res[1])
                    swap(res[0],res[1]);
                return res;
            }

        }
    }
};

方法三代码:

class Solution {
public:
    vector<int> twoSum(vector<int> &numbers, int target) {
        int i, sum;
        vector<int> results;
        map<int, int> hmap;
        for(i=0; i<numbers.size(); i++){
            if(!hmap.count(numbers[i]))
                hmap.insert(pair<int, int>(numbers[i], i));
            if(hmap.count(target-numbers[i])){
                int n=hmap[target-numbers[i]];
                if(n<i){//两个作用:自身等于target排除,若有重复,找出较小的即n
                    results.push_back(n+1);
                    results.push_back(i+1);
                    return results;
                }

            }
        }
        return results;
    }
};
时间: 2024-10-10 01:07:53

Two Sum(hashtable)的相关文章

[LeetCode] Binary Tree Maximum Path Sum(递归)

Given a binary tree, find the maximum path sum. The path may start and end at any node in the tree. For example: Given the below binary tree, 1 / 2 3 Return 6. /** * Definition for binary tree * struct TreeNode { * int val; * TreeNode *left; * TreeNo

HDU 6058 Kanade&#39;s sum(链表)

http://acm.hdu.edu.cn/showproblem.php?pid=6058 题意:找出所有区间第K大的值之和. 思路: 又有点贡献值的味道,就是考虑当前这个数贡献了几个区间. 然后往左和往右分别找大于当前数的k-1个数,这样就可以确定区间的个数,这要求我们从小到大找 并且找完之后需要删除这个数,用链表来维护. 删除元素的目的是为了加速,保证了当前查找的元素是最小值,所以只需要跳跃寻找k次就可以.具体看代码. 1 #include<iostream> 2 #include<

HDU 1003:Max Sum(DP)

Max Sum Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 142742    Accepted Submission(s): 33225 Problem Description Given a sequence a[1],a[2],a[3]......a[n], your job is to calculate the max s

1003 Max Sum(动态规划)

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) Total Submission(s): 137169    Accepted Submission(s): 31787 Problem Description Given a sequence a[1],a[2],a[3]......a[n], your job is to calculate the max sum of a

HDU-1003:Max Sum(优化)

Max Sum Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submission(s): 287192    Accepted Submission(s): 68202 Problem Description Given a sequence a[1],a[2],a[3]......a[n], your job is to calculate the max su

java数据结构——哈希表(HashTable)

哈希表提供了快速的插入操作和查找操作,每一个元素是一个key-value对,其基于数组来实现. 一.Java中HashMap与Hashtable的区别: HashMap可以接受null键值和值,而Hashtable则不能. Hashtable是线程安全的,通过synchronized实现线程同步.而HashMap是非线程安全的,但是速度比Hashtable快. 这两个类有许多不同的地方,下面列出了一部分: a) Hashtable 是 JDK 1 遗留下来的类,而 HashMap 是后来增加的.

leetcode 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

初识java集合——散列表(HashTable)

[散列表]为每个对象计算一个整数,称为散列码(是由对象的实例域产生的一个整数)更确切的说 * 不同实例域的对象产生不同的散列码 * * 如果自定义类,就要负责实现这个类的hashcode,注意:自己实现的hashcode方法应该与equals方法兼容 * 即如果a.equals(b) 为true a和b必须具有相同的散列码 * * 在java中,[散列表]用链表数组实现.每个列表被称为桶.想要查找表中对象,先计算散列码,然后与桶的总数取余 * 所的余数就是桶的索引.当桶中没有其他元素时,很幸运可

LeetCode:39. Combination Sum(Medium)

1. 原题链接 https://leetcode.com/problems/combination-sum/description/ 2. 题目要求 给定一个整型数组candidates[ ]和目标值target,找出数组中累加之后等于target的所有元素组合 注意:(1)数组中的每一个元素可以重复用:(2)数组中不存在重复元素:(3)数组中都是正整数 3. 解题思路 采用迭代的方法检验所有元素组合 4. 代码实现 1 import java.util.ArrayList; 2 import