数组
删除有序数组中的重复项
描述:
给你一个升序排列的数组 nums ,请你原地删除重复出现的元素,使每个元素只出现一次 ,返回删除后数组的新长度。元素的相对顺序应该保持一致 。
示例:
1 2 3
| 输入:nums = [1,1,2] 输出:2, nums = [1,2,_] 解释:函数应该返回新的长度 2 ,并且原数组 nums 的前两个元素被修改为 1, 2 。不需要考虑数组中超出新长度后面的元素。
|
代码1:
1 2 3 4 5 6 7 8 9 10 11 12
| class Solution { int removeDuplicates(vector<int>& nums) { if(nums.empty()) return 0; int index = 1; for(int i=1;i<nums.size();++i) { if(nums[i] != nums[index-1]) { nums[index++] = nums[i]; } } return index; } };
|
代码2:
1 2 3 4 5
| class Solution { int removeDuplicates(vector<int>& nums) { return distance(nums.begin(),unique(nums.begin(),nums.end())); } };
|
1 2 3 4 5 6 7
| template<class InputIterator> typename iterator_traits<InputIterator>::difference_type distance (InputIterator first, InputIterator last);
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
|
template <class ForwardIterator> ForwardIterator unique ( ForwardIterator first, ForwardIterator last );
template <class ForwardIterator, class BinaryPredicate> ForwardIterator unique ( ForwardIterator first, ForwardIterator last, BinaryPredicate pred );
|
删除有序数组中的重复项 II
描述:
给你一个有序数组 nums ,请你原地删除重复出现的元素,使每个元素最多出现两次 ,返回删除后数组的新长度。不要使用额外的数组空间,你必须在原地修改输入数组并在使用O(1)额外空间的条件下完成。
示例:
1 2 3
| 输入:nums = [1,1,1,2,2,3] 输出:5, nums = [1,1,2,2,3] 解释:函数应返回新长度 length = 5, 并且原数组的前五个元素被修改为 1, 1, 2, 2, 3 。 不需要考虑数组中超出新长度后面的元素。
|
代码1:
1 2 3 4 5 6 7 8 9 10 11 12
| class Solution { public: int removeDuplicates(vector<int>& nums) { if (nums.size() <= 2) return nums.size(); int index = 2; for (int i = 2; i < nums.size(); i++) { if (nums[i] != nums[index - 2]) nums[index++] = nums[i]; } return index; } };
|
单链表
反转链表
问题描述:给你单链表的头节点 $head$ ,请你反转链表,并返回反转后的链表。
示例:
示例图
输入:head = [1,2,3,4,5]
输出:[5,4,3,2,1]
输入:head = []
输出:[]
方法一:迭代
假设链表为 $1 \to 2 \to 3 \to \phi $ 我们要把它变为 $\phi \gets 1 \gets 2 \gets 3$ 。
在遍历链表时,将当前节点的 $next$ 指针改为指向前一个节点。由于节点没有引用其前一个节点,因此必须事先存储其前一个节点。在更改引用之前,还需要存储后一个节点。最后返回新的头引用。
代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| class Solution { public: ListNode* reverseList(ListNode* head) { ListNode* curr = head; ListNode* pre = nullptr; while(curr != nullptr) { ListNode *node = curr->next; curr->next = pre; pre = curr; curr = node; } return pre; } };
|
复杂度分析:
- 时间复杂度: $O(n)$ ,其中 $n$ 是链表的长度。需要遍历链表一次。
- 空间复杂度: $O(1)$
方法二:递归