1--有效的括号(20)
主要思路:
利用栈,遍历字符串,遇到左括号则入栈,遇到右括号则出栈,并判断出栈元素是否与右括号匹配;
当字符串有效时,栈为空(所有左括号都匹配出栈);当字符串无效时,则栈不为空(仍有未匹配的左括号);
#include <iostream>
#include <string>
#include <stack>
class Solution {
public:
bool isValid(std::string s) {
int len = s.length();
if (len == 0) return true;
for(int i = 0; i < len; i++){
if (s[i] == '(' || s[i] == '{' || s[i] == '['){
st.push(s[i]);
}
else if(s[i] == ')' && !st.empty()){
char c = st.top();
st.pop();
if (c != '(') return false;
}
else if(s[i] == '}' && !st.empty()){
char c = st.top();
st.pop();
if (c != '{') return false;
}
else if(s[i] == ']' && !st.empty()){
char c = st.top();
st.pop();
if (c != '[') return false;
}
else
return false;
}
return st.empty();
}
private:
std::stack<char> st;
};
int main(int argc, char *argv[]){
std::string test = "()[]{}";
Solution S1;
bool res = S1.isValid(test);
if(res) std::cout << "true" << std::endl;
else std::cout << "false" << std::endl;
return 0;
}
2--合并两个有序链表(21)
主要思路:
归并排序,分别遍历比较两个链表的结点,数值小的结点归并到新链表中;
#include <iostream>
#include <string>
#include <stack>
struct ListNode {
int val;
ListNode *next;
ListNode() : val(0), next(nullptr) {}
ListNode(int x) : val(x), next(nullptr) {}
ListNode(int x, ListNode *next) : val(x), next(next) {}
};
class Solution {
public:
ListNode* mergeTwoLists(ListNode* list1, ListNode* list2) {
if(list1 == NULL && list2 == NULL) return NULL;
ListNode* head = new ListNode();
ListNode* l_back = head; // 指向新链表最后一个结点
ListNode* l1 = list1;
ListNode* l2 = list2;
while(l1 != NULL && l2 != NULL){
if(l1->val < l2->val){
l_back->next = l1;
l1 = l1->next;
l_back = l_back->next;
}
else{
l_back->next = l2;
l2 = l2->next;
l_back = l_back->next;
}
}
if(l1 == NULL) l_back->next = l2;
if(l2 == NULL) l_back->next = l1;
return head->next;
}
};
int main(int argc, char *argv[]){
ListNode* Node1 = new ListNode(1);
ListNode* Node2 = new ListNode(2);
ListNode* Node3 = new ListNode(4);
Node1->next = Node2;
Node2->next = Node3;
ListNode* Node4 = new ListNode(1);
ListNode* Node5 = new ListNode(3);
ListNode* Node6 = new ListNode(4);
Node4->next = Node5;
Node5->next = Node6;
Solution S1;
ListNode* l = S1.mergeTwoLists(Node1, Node4);
while(l != NULL){
std::cout << l->val << " ";
l = l->next;
}
return 0;
}
3--括号生成(22)
主要思路:视频讲解
递归遍历第 num 个字符是属于左括号还是右括号,递归终止条件是剩下的左括号和右括号数为 0;
有效的括号组合必须是当前剩下的右括号数必须大于剩下的左括号数;
#include <iostream>
#include <string>
#include <vector>
class Solution {
public:
std::vector<std::string> generateParenthesis(int n) {
recur(n, n, 0);
return Res;
}
// 还剩下 left 个和 right 个左括号和右括号,当前要填第 num 个字符
void recur(int left, int right, int num){
if(left == 0 && right == 0){
c[num] = 0;
Res.push_back(c);
return;
}
if(left){ // 剩下的左括号不为 0
c[num] = '(';
recur(left - 1, right, num + 1);
}
if(left < right){ // 剩下的右括号必须大于剩下的左括号
c[num] = ')';
recur(left, right - 1, num + 1);
}
}
private:
std::vector<std::string> Res;
char c[20];
};
int main(int argc, char *argv[]){
int n = 3;
Solution S1;
std::vector<std::string> Res = S1.generateParenthesis(n);
for(std::string value : Res){
std::cout << value << std::endl;
}
return 0;
}
4--合并K个升序链表(23)
主要思路: