体会思想的题目:
111.二叉树的最小深度
没看懂题解,(insert)
class Solution {
public:
bool canPartitionKSubsets(vector& nums, int k) {
//排除一些特殊情况
if(k>nums.size()){
return false;
}
int sum=0;
for(int v:nums){
sum+=v;
}
if(sum%k!=0){
return false;
}
int used=0;//使用位图技巧
int target=sum/k;
//K号桶初始什么都没装,从nums[0]开始做选择
return backtrack(k,0,nums,0,used,target);
}
unordered_mapmemo;
bool backtrack(int k,int bucket,vectornums,int start,int used,int target){
//base case
if(k==0){
return true;
}
if(bucket==target){
//装满了当前桶,递归穷举下一个桶的选择
//让下一个桶从nums[0]开始选数字
bool res=backtrack(k-1,0,nums,0,used,target);
//缓存结果
memo.insert(used,res);
return res;
}
if(memo.find(used)]){
//避免冗余计算
return memo[used];
}
for(int i=start;i>i)&1){
//判断第i位数是否是1
//nums[i]已经被装入别的桶中
continue;
}
if(nums[i]+bucket>target){
continue;
}
//做选择
used|=1<
1.
l1是一个向量
int n1 = l1 ? l1->val: 0;
三目运算符,若l1不是空指针,则返回l1的value,
2.
vector
【c/c++】string、vector和数组_jiangwei0512的博客-CSDN博客
3.这种for循环的形式
for(auto&row:mat){
for(char ch:row){
if(ch){
ans+=ch;
}
}
}
4.vector 用法
vector
sums.resize(m,vector
class Solution {
public ListNode mergeTwoLists(ListNode l1, ListNode l2) {
// 虚拟头结点
ListNode dummy = new ListNode(-1), p = dummy;
ListNode p1 = l1, p2 = l2;
while (p1 != null && p2 != null) {
// 比较 p1 和 p2 两个指针
// 将值较小的的节点接到 p 指针
if (p1.val > p2.val) {
p.next = p2;
p2 = p2.next;
} else {
p.next = p1;
p1 = p1.next;
}
// p 指针不断前进
p = p.next;
}
if (p1 != null) {
p.next = p1;
}
if (p2 != null) {
p.next = p2;
}
return dummy.next;
}
}
// 详细解析参见:
// https://labuladong.github.io/article/?qno=21
c++数组的长度用size来判断,而不是length
V利用vector实现一对一(pair<int,int>)_天天向上的菜鸡杰!!的博客-CSDN博客_vector
vector
stack
s.empty() left.top())
class Solution {
public:
vector nextGreaterElement(vector& nums1, vector& nums2) {
//记录nums2的每个元素的下一个更大的元素
vectorgreater=nextGreaterElement(nums2);
//转化成映射
unordered_setgreaterMap;
for(int i=0;ires(nums1.size());
for(int i=0;inextGreaterElement(vectornums){
int n=nums.size();
vectorres(n);
stacks;
for(int i=n-1;i>=0;i--){
//判定个子高矮
while(!s.empty()&&s.top()<=nums[i]){
s.pop();
}
res[i]=s.empty()?-1:s.top();
s.push(nums[i]);
}
return res;
}
};
vector
vector
106题目,想不明白哪里出错了
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* TreeNode *left;
* TreeNode *right;
* TreeNode() : val(0), left(nullptr), right(nullptr) {}
* TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
* TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}
* };
*/
class Solution {
private:
unordered_mapvalToIndex;
public:
TreeNode* buildTree(vector& inorder, vector& postorder) {
for(int i=0;iinorder,int inStart,int inEnd,vectorpostorder,int postStart,int postEnd){
if(inStart>inEnd){
return nullptr;
}
//root节点对应的值是后续遍历的最后一个
TreeNode *root=new TreeNode(postorder[postEnd]);
int index=valToIndex[inorder[postorder[postEnd]]];
int leftSize=index-inStart;
//递归构造左右子树
root->left=build(inorder,inStart,index-1,postorder,postStart,postStart+leftSize-1);
root->right=build(inorder,index+1,inEnd,postorder,postStart+leftSize,postEnd-1);
return root;
}
};
整数变成字符
#include
using namespace std;
#include
//目标 vector容器存放自定义的数据类型
class Person {
public:
string m_Name;
int m_Age;
//构造函数:
Person(string name, int age) {
this->m_Name = name;
this->m_Age = age;
}
};
void test01(){
vectorv;
Person p1("p1", 1);
Person p2("p2", 1);
Person p3("p3", 1);
Person p4("p4", 1);
Person p5("p5", 1);
//向容器中添加数据包
v.push_back(p1);
v.push_back(p2);
v.push_back(p3);
v.push_back(p4);
v.push_back(p5);
//遍历容器中的数据,*it是什么是一个Person的数据类型,解决指针 it是一个指针,可以->出来属性
for (vector::iterator it = v.begin(); it != v.end(); it++) {
cout << "姓名:" << (*it).m_Name << "年龄:"<<(*it).m_Age<m_Name << "年龄:" << it->m_Age << endl;
}
}
int main() {
test01();
return 0;
}
力扣 215. 数组中的第K个最大元素
class Solution {
public:int findKthLargest(vectornums, int k) {
// 小顶堆,堆顶是最小元素
priority_queue pq ;
for (int e : nums) {
// 每个元素都要过一遍二叉堆
pq.push(e);
// 堆中元素多于 k 个时,删除堆顶元素
if (pq.size() > k) {
pq.pop();
}
}
// pq 中剩下的是 nums 中 k 个最大元素,
// 堆顶是最小的那个,即第 k 个最大元素
return pq.top();
}
};
// 详细解析参见:
// https://labuladong.github.io/article/?qno=215
315. 计算右侧小于当前元素的个数
class Merge{
private:static vectortemp;
public:static void sort(vectornums){
//先给辅助数组开辟内存空间
temp.resize(nums.size());
//排序整个数组(原地修改)
sort(nums,0,nums.size()-1);
}
//将子数组nums[lo..hi]进行排序
private: static void sort(vectornums,int lo,int hi){
if(lo==hi){
//单个元素不用排序
return;
}
//这样写为了防止移出
int mid=lo+(hi-lo)/2;
//先对左半部分数组 nums[lo..mid]排序
sort(nums,lo,mid);
//再对右半部分数组nums[mid+1..hi]排序
sort(nums,mid+1,hi);
//将两部分合并成一个有序数组
merge(nums,lo,mid,hi);
}
private: static void merge(vectornums,int lo,int mid,int hi){
//先把[lo..hi]复制到辅助数组中
//以便合并后的结果可以直接存入nums
for(int i=lo;i<=hi;i++){
temp[i]=nums[i];
}
//数组双指针技巧,合并两个有序数组
int i=lo,j=mid+1;
for(int p=lo;p<=hi;p++){
if(i==mid+1){
//左半数组已被全部合并
nums[p]=temp[j++];
}else if(j==hi+1){
//右半边数组已经被全部合并
nums[p]=temp[i++];
}else if(temp[i]>temp[j]){
nums[p]=temp[j++];
}else{
nums[p]=temp[i++];
}
}
}
};
class Solution {
public:
vector countSmaller(vector &nums) {
Merge mysolution;
mysolution.sort(nums);
return nums;
}
};
备份代码,虽然是错的
class Pair{
public:int val,id;
public:Pair() =default;
Pair(int val,int id){
//记录元素的值得
this->val=val;
//记录元素id
this->id=id;
}
};
class Solution {
public:
public:
//归并排序用到的辅助数组
vector temp;
// // 记录每个元素后面比自己小的元素个数
vectorcount;
//主函数
vector countSmaller(vector&nums) {
int n=nums.size();
temp.resize(n);
count.resize(n);
vectorarr(n);
//记录元素的原始索引位置,以便在 count 数组中更新结果
for(int i=0;ires;
for(int c:count){
res.push_back(c);
}
return res;
}
//归并排序
private:void sort(vectorarr,int lo,int hi){
if (lo==hi){
return ;
}
int mid=lo+(hi-lo)/2;
sort(arr,lo,mid);
sort(arr,mid+1,hi);
merge(arr,lo,mid,hi);
}
//合并两个有序数组
private:void merge(vectorarr,int lo,int mid,int hi){
for(int i=lo;itemp[j].val){
arr[p]=temp[j++];
}else{
arr[p]=temp[i++];
//更新count数组
count[arr[p].id] += j - mid - 1;
}
}
}
};
字符串默认以0为结尾
cin.peek();
cin.get();
cin.read();
推荐const int size=50;
char buf[size];
cin.gcount()计数
cout.write(buf,20);
cin.getline(buf,10);
获得10个
cout两个方法
c++关键词太多,语法太多,太灵活
文件I/O
编写文件复制任务
在方法之前声明变量
207. 课程表
class Solution {
//记录一次traverse递归经过的节点
vectoronPath;
//记录遍历过的节点,防止走回头路
vectorvisited;
//记录途中是否有环
bool hasCycle=false;
public:
bool canFinish(int numCourses, vector>& prerequisites) {
vectorgraph=buildGraph(numCourses,prerequisites);
vectorvisited[numCourses];
vectoronPath[numCourses];
for(int i=0;igraph,int s){
if(onPath[s]){
//出现环
hasCycle=true;
}
if(visited[s]||hasCycle){
//如果已经找到了环,也不用遍历了
return;
}
//前序遍历位置代码
visited[s]=true;
onPath[s]=true;
for(int t:graph[s]){
traverse(graph,t);
}
//后序遍历位置代码
onPath[s]=false;
}
vectorbuildGraph(int numCourses,vector>prerequisites){
//图中共有numCOurses个节点
vectorgraph[numCourses];
for(int i=0;igraph[i];
}
for(vectoredge:prerequisites){
int from=edge[1];
int to=edge[0];
//修完课程from才能修课程to
//在图中添加一条从from指向to 的有向边
graph[from].push_back(to);
}
return graph;
}
};
DPS:深度优先搜索
尝试自己解决216组合总和三,代码不对,没找到问题
class Solution {
vector>res;
vectortrack;
int trackSum;
vectornums={1,2,3,4,5,6,7,8,9};
public:
vector> combinationSum3(int k, int n) {
backtrack(nums,0,k,n);
return res;
}
void backtrack(vectornum,int start,int k,int n){
if(trackSum>n){
return ;
}
if(trackSum==n){
res.push_back(track);
return ;
}
if(track.size()>k){
return ;
}
for(int i=start;i0&&(num[i-1]==num[i])){
continue;
}
track.push_back(num[i]);
trackSum+=num[i];
backtrack(num,i+1,k,n);
trackSum-=num[i];
track.pop_back();
}
}
};
函数加或者不加&差别很大
class Solution {
public:
int maxAreaOfIsland(vector>& grid) {
int res=0;
int m=grid.size();
int n=grid[0].size();
for(int i=0;i>&grid,int i,int j){
int m = grid.size(), n = grid[0].size();
if (i < 0 || j < 0 || i >= m || j >= n) {
// 超出索引边界
return 0;
}
if (grid[i][j] == 0) {
// 已经是海水了
return 0;
}
// 将 (i, j) 变成海水
grid[i][j] = 0;
return dfs(grid, i + 1, j)
+ dfs(grid, i, j + 1)
+ dfs(grid, i - 1, j)
+ dfs(grid, i, j - 1) + 1;
}
};
加&符号和不加&有很大区别1020飞地的数量
class Solution {
public:
int numEnclaves(vector>& grid) {
int m=grid.size();
int n=grid[0].size();
for(int i=0;i>&grid,int i,int j){
int m=grid.size();
int n=grid[0].size();
if(i<0||j<0||i>=m||j>=n||grid[i][j]==0){
return;
}
grid[i][j]=0;
dfs(grid,i+1,j);
dfs(grid,i,j+1);
dfs(grid,i-1,j);
dfs(grid,i,j-1);
}
};
queue
{
两个操作:emplace
pop
}
这是什么语法,来自752题
931. 下降路径最小和
class Solution {
public:
int minFallingPathSum(vector>& matrix) {
int n=matrix.size();
int res=INT_MAX;
//将备忘录的值初始化为6666;
vector>memo[n][n];
for(int i=0;i>memo;
int dp(vector>&matrix,int i,int j){
//1.索引合法性检查
if(i<0||j<0||i>=matrix.size()||j>=matrix[0].size()){
return 99999;
}
//2.base case
if(i==0){
return matrix[0][j];
}
//3.查找备忘录,防止重复计算
if(memo[i][j]!=66666){
return memo[i][j];
}
//进行状态转移
memo[i][j]=matrix[i][j]+zuixiao(dp(matrix,i-1,j),dp(matrix,i-1,j-1),dp(matrix,i-1,j+1));
return memo[i][j];
}
int zuixiao(int a,int b,int c){
return min(a,min(b,c));
}
};
找不到错误,就是不能运行
vector的用法:
712题目
class Solution {
public:
vector>memo;
int minimumDeleteSum(string s1, string s2) {
int m=s1.size();
int n=s2.size();
//
vector>memo(m,vector(n));
for(int i=0;i
class Solution {
public:
int countSquares(vector>& matrix) {
if(matrix.size()==0||matrix[0].size==0){
return 0;
}
int maxSide=0;
int rows=matrix.size(),columns=matrix[0].size();
for(int i=0;i
6148. 矩阵中的局部最大值
剑指 Offer II 040. 矩阵中最大的矩形 - 力扣(LeetCode)
class Solution {
public:
int maxProfit(vector& prices) {
int n=prices.size();
int buy1=-prices[0];
int sell1=0;
int buy2=-prices[0];
int sell2=0;
for(int i=1;i
地下城游戏
class Solution {
public:
int calculateMinimumHP(vector>& dungeon) {
int m=dungeon.size();
int n=dungeon[0].size();
vector>dp(m,vector(n));
dp=dungeon;
for(int i=0;i
这里出现的问题是总会有一个溢出,找不到原因
174题目,力扣
class Solution {
public:
vector>memo;
int calculateMinimumHP(vector>& dungeon) {
int m=dungeon.size();
int n=dungeon[0].size();
vector> memo(m,vector(n,-1));
return dp(dungeon,0,0);
}
int dp(vector>&grid,int i,int j){
//base case
int m=grid.size();
int n=grid[0].size();
if(i==m-1&&j==n-1){
return grid[i][j]>=0?1:1-grid[i][j];
}
if(i==m||j==n){
return INT_MAX;
}
if(memo[i][j]!=-1){
return memo[i][j];
}
int res=min(dp(grid,i+1,j),dp(grid,i,j+1))-grid[i][j];
memo[i][j]=res<=0?1:res;
return memo[i][j];
}
};
C++的遍历
两个问题,(1)为什么会有返回值,null(2)为什么auto &可以代表一个向量
力扣
#include
#include
#include
#include
using namespace std;
int main(){
int n,m;
cin>>n;
cin>>m;
vector>shouyi;
for(int i=0;i>shouyi[i][j];
}
}
int sum=0;
for(int i=0;i
cout< getline是干啥用的? 字符串的结束的标志 #include 新建一个动态数组 int *p=new int[n]; 统计字符串中子串出现的次数_牛客题霸_牛客网 子类中调用父类构造_牛客题霸_牛客网 重写子类的计算逻辑c++从键盘输入数组
using namespace std;
#include
int main()
{
char ch;
int n;
vector
cout << "以空格为间隔输入一组数据:";
while (1) {
cin >> n;
nums.push_back(n);
if (cin.get() == '\n')
break;
}
cout << "输入的数据为:" << endl;
for (int i = 0;i < nums.size();i++) {
cout << nums[i] << endl;
}
return 0;
}交换两个数字
#include
#include
Find函数的用法
#include
str.length
用数组操作字符串的错误
#include
#include
子类中调用父类的构造
#include
#include
C++ make_pair的用法