首先想到是肯定是暴力破解法:
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
vector<int> vec;
for(int i = 0; i < nums.size();++i)
{
for(int j = i + 1 ; j < nums.size();++j)
{
if(nums[i] + nums[j] == target)
{
vec.push_back(i);
vec.push_back(j);
break;
}
}
}
return vec;
}
};
这个不够完美,因为是暴力法,在很多方面都存在自己的缺陷
下面这个是利用哈希表的解法
class Solution {
public:
vector<int> twoSum(vector<int>& nums, int target) {
unordered_map<int, int> hash;
for(int i = 0; i < nums.size(); i++){
if(hash.count(target - nums[i])) return {hash[target - nums[i]], i};
hash[nums[i]] = i;
}
return {-1, -1};
}
};
时间复复杂度减低了,但是内存的消耗却提升了。
//是我刚开始给出的代码,但是有的测试用例不能跑过,原因是因为,我采用的是计数然后求和,但是结点可以很多,但是数字不能特别大。所以有的用例不能跑过
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode(int x) : val(x), next(NULL) {}
* };
*/
class Solution {
public:
int func(ListNode* l1)
{
unsigned int ret = 0;
if(l1->next)
{
ret = func(l1->next);
}
return (ret * 10) + l1->val;
}
ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
unsigned int ret = func(l1) + func(l2);
ListNode* p = new ListNode(ret % 10);
ListNode* p1 = p;
ret = ret / 10;
while(ret / 10 != 0 || ret % 10 != 0)
{
p1->next = new ListNode(ret % 10);
ret = ret / 10;
p1 = p1->next;
}
p1->next = nullptr;
return p;
}
};
下面是我重新写的代码:
//这个是可以通过全部测试用例的代码
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode(int x) : val(x), next(NULL) {}
* };
*/
class Solution {
public:
ListNode* addTwoNumbers(ListNode* l1, ListNode* l2) {
vector<int> vec1;
vector<int> vec2;
ListNode* cur = l1;
while (cur != nullptr)
{
vec1.push_back(cur->val);
cur = cur->next;
}
cur = l2;
while (cur != nullptr)
{
vec2.push_back(cur->val);
cur = cur->next;
}
if (vec1.size() < vec2.size()) //因为是两个数相加,所以得知道哪一个数子比较长
{
swap(vec1, vec2);
}
vector<int> vec3;
vec3.resize(vec1.size() + 1); //多开辟一个空间,防止199 + 9 这样的数字。最后有进位
int size1 = vec1.size();
int size2 = vec2.size();
int i = 0;
int flag = 0;
while (i < size1) //长的数字在外面
{
if (i < size2) //短的数字在里面
{
int ret = vec1[i] + vec2[i] + flag;
flag = 0;
if (ret >= 10)
{
vec3[i] = ret % 10;
flag = 1;
}
else
vec3[i] = ret;
}
else
{
int ret = vec1[i] + flag;
flag = 0;
if (ret >= 10)
{
vec3[i] = ret % 10;
flag = 1;
}
else
vec3[i] = ret;
}
i++;
}
if (flag == 1) //最后再判断一次是否存在进位问题
vec3[i] = 1;
else
vec3.erase(vec3.end() - 1); //要是不存在的话就删除最后的一个位置
ListNode* p = new ListNode(vec3[0]); //最后拿着数组去拼装链表
ListNode* p1 = p;
for (int i = 1; i < vec3.size(); ++i)
{
p1->next = new ListNode(vec3[i]);
p1 = p1->next;
}
p1->next = nullptr;
return p;
}
};
但是这段代码的时间复杂度比较高,是因为在while循环内部做了太多的相同操作的判断
于是对这段代码进行优化
while (i < size1)
{
int ret;
if (i < size2)
ret = vec1[i] + vec2[i] + flag;
else
ret = vec1[i] + flag;
flag = 0;
if (ret >= 10)
{
vec3[i] = ret % 10;
flag = 1;
}
else
vec3[i] = ret;
i++;
}
优化后的结果,如图所示:
、