递归与回溯(一)

递归

递归一定要有出口,不然会无限调用,死循环

string fun(int n){if(n==0)return "a";if(n==1)return "b";return fun(n - 1) + fun(n - 2);
}

输出前8种结果:

在这里插入图片描述


双写数字递归例子

注意递归的return

int doubleNum(int n){if (n < 10){return (10 * n) + n;}else{int a = doubleNum(n / 10);int b = doubleNum(n % 10);return (100 * a) + b;}
}

以:1987为例说明递归顺序,由于每次递归都copy一次函数副本,只有return,才能结束递归的调用。

在这里插入图片描述

例子2,不管是谁递归,大小以递归数字为准

string func(string s){if (s.size()==1){return s+=s;//双写}else{string a = func(s.substr(1));//去掉第一个字母string b = func(s.substr(0,s.size()-1));//去掉最后一个字母return a+b;}
}

func(“abc”)结果是:ccbbbbaa

在这里插入图片描述

递归判断回文串

bool ishuiwen(string s){//最基本情况,递归出口if (s.size()<=1){//s是单个字符或者空,是回文return true;}else{char first = s[0];char last = s[s.size() - 1];//middle是去掉首位两字符的字符串string middle = s.substr(1, s.size() - 2);return (first == last && ishuiwen(middle));}

打印所有二进制

也就是给定数字n,打印出n的所有可能二进制排列

比如:

n=1 — 0,1

n=2 — 00,01;10,11

n=3 —000,001,010,011;100,101,110,111

发现规律:
n=1  {0},{1}
n=2  {00},{01};{10},{11}
n=3  {000},{001},{010},{011}{100},{101},{110},{111}
---所以后一个是前一个所有可能分别加上0和1构成新集合
---也就是n=4是n=3的所有结果,分别插入0和1
n=4
{0 000},{0 001},{0 010},{0 011},{0 100},{0 101},{0 110},{0 111}
{1 000},{1 001},{1 010},{1 011},{1 100},{1 101},{1 110},{1 111}

解:

vector<vector<int> > printfAllBin(int n){//base case,递归结束if(n==0)  return {{}};//递归求结果vector<vector<int>> res=printfAllBin(n-1);//对上一步进行操作得到下一步//这里是对当期的二进制结果前,加0或加1然后存储新结果int size = res.size();//这个是循环结束标志,每次递归res的大小都不同for (int i = 0; i < size;i++){auto tmp = res[i];tmp.push_back(0);//加0res.push_back(tmp);//加一res[i].push_back(1);}return res;
}

在这里插入图片描述

vector<vector<int> > printfAllBin(int n){//base case,递归结束if(n==0)  return {{}};//递归求结果vector<vector<int>> res;vector<vector<int>> cur= printfAllBin(n - 1);//cur作为当前res,更新下一次resfor(auto& val:cur){//记录val值后加入1auto tmp = val;tmp.push_back(1);//原有val值加0val.push_back(0);//把结果都装入res中res.push_back(tmp);res.push_back(val);}return res;
}

这里用cur记录当前递归结果,然后加入0和1后,放入res中

子集和问题

78. 子集

求1个数组的子集和

以1,2,3为例

顺着思想 f : \text{顺着思想}f\text{:} 顺着思想f

f ( { } ) = { } f\left( \left\{ \right\} \right) =\left\{ \right\} f({})={}

f ( { 1 } ) = f ( { } ) + 1 = { } , { 1 } f\left( \left\{ 1 \right\} \right) =f\left( \left\{ \right\} \right) +1=\left\{ \right\} \text{,}\left\{ 1 \right\} f({1})=f({})+1={}{1}

f ( { 1 , 2 } ) = f ( { 1 } ) + 2 = { } , { 1 } , { 2 } , { 1 , 2 } f\left( \left\{ 1,2 \right\} \right) =f\left( \left\{ 1 \right\} \right) +2=\left\{ \right\} ,\left\{ 1 \right\} ,\left\{ 2 \right\} ,\left\{ 1,2 \right\} f({1,2})=f({1})+2={},{1},{2},{1,2}

f ( 1 , 2 , 3 ) = f ( { 2 } ) + 3 = { } , { 1 } , { 2 } , { 1 , 2 } , { 3 } , { 1 , 3 } , { 2 , 3 } , { 1 , 2 , 3 } f\left( 1,2,3 \right) =f\left( \left\{ 2 \right\} \right) +3=\left\{ \right\} ,\left\{ 1 \right\} ,\left\{ 2 \right\} ,\left\{ 1,2 \right\} ,\left\{ 3 \right\} ,\left\{ 1,3 \right\} ,\left\{ 2,3 \right\} ,\left\{ 1,2,3 \right\} f(1,2,3)=f({2})+3={},{1},{2},{1,2},{3},{1,3},{2,3},{1,2,3}

也就是 f ( { 1 , . . , n } ) = f ( { 1 , . . , n − 1 } ) ∪ f ( { 1 , . . , n − 1 } ) 的每一个子集加n \text{也就是}f\left( \left\{ 1,..,n \right\} \right) =f\left( \left\{ 1,..,n-1 \right\} \right) \cup \ f\left( \left\{ 1,..,n-1 \right\} \right) \text{的每一个子集加n} 也就是f({1,..,n})=f({1,..,n1}) f({1,..,n1})的每一个子集加n

正向解法:

 vector<vector<int>> subsets(vector<int>& nums) {// f({1,..n})=f({1,..,n-1}) U f({1,..,n-1})+nvector<vector<int>> res({{}});for(int i=0;i<nums.size();i++){int n=res.size();//----这个n很重要,限定了当前res的增长for(int j=0;j<n;j++){//现有元素装入resres.push_back(res[j]);//res元素都加上nums[i]res[j].push_back(nums[i]);}}return res;}

递归做法:

一个典型的递归结构:

  • [1,2,3] 的子集可以由 [1,2] 追加得出,[1,2] 的子集可以由 [1] 追加得出

  • base case 显然就是当输入集合为空集时,输出子集也就是一个空集。

  • 递归出口是:{{}}—这里是vector<vector<>>

  • 解题关键就是:当前子集和=上一个子集和∪{上一个子集加上多出的元素}

  • 也就是:每次从尾部取出一个元素,然后计算当前子集和和该元素的情况

    思维如下:

在这里插入图片描述

vector<vector<int>> subsets(vector<int>& nums) {vector<vector<int>> res;//递归出口if(nums.size()==0)   return {{}};//从尾部减少一个元素int x=nums.back();//减少元素后的集合auto set=nums;set.pop_back();//去掉元素/*当前子集和元素*/for(auto& val:subsets(set)){vector<int> choose_cur =val;choose_cur.push_back(x);//res加入选它的和原来的(不选)res.push_back(val);res.push_back(choose_cur);}return res;}
vector<vector<int>> subsets(vector<int>& nums) {vector<vector<int>> res;//递归出口if(nums.size()==0) return {{}};//每次去掉nums前面元素int x=nums.front();nums.erase(nums.begin());//去掉x//记录递归子集vector<vector<int>> set=subsets(nums);//回退中:前一个生成后一个的操作for(auto& val:set){auto tmp=val;tmp.push_back(x);//res插入两种情况res.push_back(val);//不选择xres.push_back(tmp);//选择x}return res;}

subsets(set)需要新的变量,不可以直接用res,因为auto遍历,res有push_back操作,会造成死循环

每次从nums去掉前一个或后一个都可以,只要能生成待插值即可

全排列问题

在这里插入图片描述

和前面类似,后面的也可以由前面的生成,规律就是:每一个元素插空

比如对d,其中一个子集{c,b,a}中:__c__b__a__,d可以选择__任一处
所以:4乘以{a,b,c}的6种情况,4!=24

难点在于:前一个到后一个的插空

思路:首先原有的一个,直接在最前面插作为结果

​ 然后接下来,从最后一个开始遍历当前字符串,每次插入x后作为结果保存在res中

在这里插入图片描述

  • 首先先看一个插值方法
void traverse(const vector<vector<int>>& res){for(auto aa:res){for(auto bb:aa){cout << bb << " ";}cout << endl;}
}
int main(){vector<int> nums = {1, 2, 3, 4, 5};vector<vector<int>> res;for (auto it = nums.begin();it<=nums.end();it++){//mm在it位置插入6,此时it指向了新值it = nums.insert(it, 6);//mm放入resres.push_back(nums);//(6),5,1,2,3,4//mm删除插入新值,不影响下一个插入it=nums.erase(it);//it回到原来的1}traverse(res);return 0;
}

在这里插入图片描述

巧用erase和insert,但是记住返回值是下一个迭代器

本题解法:

vector<vector<int>> fullLine(const vector<int>& nums){vector<vector<int>> res;if(nums.size()==0) return {{}};int x = nums.back();//待考虑值vector<int> mm = nums;mm.pop_back();res = fullLine(mm);int n = res.size();for (int i = 0; i < n;i++){auto tmp = res[i];res[i].insert(res[i].begin(), x);//考察插入for (auto it = tmp.end(); it != tmp.begin();it--){it = tmp.insert(it, x);res.push_back(tmp);tmp.erase(it);}}return res;
}
vector<vector<int>> fullLine(const vector<int>& nums){vector<vector<int>> res;if(nums.size()==0) return {{}};int x = nums.back();//待考虑值vector<int> mm = nums;mm.pop_back();auto set = fullLine(mm);for (auto& val:set){auto tmp =val;val.insert(val.begin(), x);res.push_back(val);//考察插入for (auto it = tmp.end(); it != tmp.begin();it--){it = tmp.insert(it, x);res.push_back(tmp);tmp.erase(it);}}return res;
}

前一个靠n来结束循环

后一个res得装所有新的结果

面试题 08.07. 无重复字符串的排列组合

 vector<string> permutation(string S) {vector<string> res;//S.size()==0if(S=="") return {""};//注意是:vector<string>char x=S.back();S.pop_back();res=permutation(S);cout<<x<<endl;int n=res.size();for(int i=0;i<n;i++){auto tmp=res[i];res[i].insert(res[i].begin(),x);for(auto it=tmp.end();it!=tmp.begin();it--){it=tmp.insert(it,x);res.push_back(tmp);tmp.erase(it);}}return res;}

char x=S[0]; res=permutation(S.substr(1));

c++字符串和容器使用完全一致

 vector<string> permutation(string S) {vector<string> res;if(S.size()==0) return {""};//注意是:vector<string>char x=S[0];auto set=permutation(S.substr(1));for(auto& val:set){auto tmp=val;val.insert(val.begin(),x);res.push_back(val);for(auto it=tmp.end();it!=tmp.begin();it--){it=tmp.insert(it,x);res.push_back(tmp);tmp.erase(it);}}return res;}

回溯

嵌套循环与递归回溯

传入nums数组,请选择其中的n个,输出大小为n的所有排列可能

ex: nums={1,2,3}

则n=2的可能:{1,1},{1,2},{1,3},{2,1},{2,2},{2,3},{3,1},{3,2},{3,3}

假设n=3时,则迭代写法为:

vector<vector<int>> fun_loop(const vector<int>& nums){vector<vector<int>> res;vector<int> tmp;int n = nums.size();for (int i = 0; i < n;i++){tmp.push_back(nums[i]);for (int j = 0; j < n;j++){tmp.push_back(nums[j]);for (int k = 0; k < n;k++){tmp.push_back(nums[k]);res.push_back(tmp);tmp.pop_back();}tmp.pop_back();}tmp.pop_back();}return res;
}

注意:前一层回到上一层需要放弃前一层所选的元素,不然结果会保留上一次的结果

递归写法:

​ 发现迭代写法的特点,每次for的时候都会放入当前下标的值nums[下标],然后for结束前,也就是内层循环回退到外层循环时,都需要pop也就是放弃已选的元素。这是天然的递归结构

不过在参数传递上,递归时候:递归的函数拷贝当前结果继续使用,所以必须将重要的参数保留

递归函数参数
  • 要么作为全局变量
  • 要么作为函数参数传递,为了保留结果,需要指针或引用方式传递

本题需要递归出口和每次需要加元素存储的vector

------递归出口level,也就是嵌套循环层数

------vector tmp,一个符合要求得到结果

vector<vector<int>> res;
vector<vector<int>> fun_recursion(const vector<int>& nums,vector<int> ans,int level){int n = nums.size();for (int i = 0; i < n;i++){//递归出口if(level==3){ans.push_back(nums[i]);res.push_back(ans);ans.pop_back();}//回溯else{ans.push_back(nums[i]);fun_recursion(nums, ans, level + 1);ans.pop_back();}}return res;
}

可以把放元素和放弃元素放在if,else外面

vector<vector<int>> res;//全局变量
vector<vector<int>> fun_recursion(const vector<int>& nums,vector<int> ans,int level){int n = nums.size();for (int i = 0; i < n;i++){//放元素ans.push_back(nums[i]);//递归出口if(level==3){res.push_back(ans);}//回溯else{fun_recursion(nums, ans, level + 1);}//放弃当前元素ans.pop_back();}return res;
}

在这里插入图片描述

从结果上来说就是:

在这里插入图片描述

当然也可以把全局变量res作为函数参数,但是需要引用&,因为上一层的结果需要保留

vector<vector<int>> fun_recursion(const vector<int>& nums,vector<int> ans,int level,\vector<vector<int>>& res){int n = nums.size();for (int i = 0; i < n;i++){//放元素ans.push_back(nums[i]);//递归出口if(level==3){res.push_back(ans);}//回溯else{fun_recursion(nums, ans, level + 1,res);}//放弃当前元素ans.pop_back();}return res;
}

主函数:

    vector<int> nums = {11, 22, 33};vector<int> mm;vector<vector<int>> it;auto res=fun_recursion(nums,mm,1,it);

这里递归结束没有return,因为level=3这层for是需要的,也可以把level=4作为递归结束条件,放在程序前。

vector<vector<int>> res;
vector<vector<int>> fun_recursion(const vector<int>& nums,vector<int> ans,int level){int n = nums.size();//递归出口if(level==4){res.push_back(ans);return res;}for (int i = 0; i < n;i++){//放元素ans.push_back(nums[i]);//回溯fun_recursion(nums, ans, level + 1);//放弃当前元素ans.pop_back();}return res;
}

全排列问题

嵌套循环

用迭代写法写出只有三个元素的全排列

在这里插入图片描述

但是在内层返回外层时候,需要放弃已选择该层元素

在这里插入图片描述

int main()
{vector<int> nums = {11, 22, 33};vector<vector<int>> res;// 迭代法求3个元素全排列// 选1;下一个从2,3中选2;最后只能选3for (int i = 0; i < nums.size();i++){vector<int> tmp;tmp.push_back(nums[i]);for (int j = 0; j < nums.size();j++){if(j==i)continue;tmp.push_back(nums[j]);for (int k = 0; k < nums.size();k++){if(k==i || k==j)continue;tmp.push_back(nums[k]);//把符合的结果装入resres.push_back(tmp);//抛去已选的ktmp.pop_back();}//ktmp.pop_back();//回到j前,抛去已选的k}//j}//itraverse(res);return 0;
}

迭代法解决全排列问题只能限定元素个数

比如:10个元素10层循环,而且10个for也解决不聊9个元素的循环

静态性:代码仅局限于一个具体问题的求解,而不是一类问题的求解。

递归回溯

循环嵌套自带有回溯能力,内层循环结束会回到它的上一层循环继续执行。

如何放弃重复的元素不选,也就是直接跳过这次结果,方法:设置标记,如果标记后,for不执行本次结果

vector<bool> flag;
vector<vector<int>> res;
vector<vector<int>> fullLine(const vector<int>& nums,vector<int> ans,int level){int n = nums.size();for (int i = 0; i <n;i++){if(!flag[i]){//放元素ans.push_back(nums[i]);flag[i] = true;//该元素已选择if(level==3){//不再递归res.push_back(ans);}else{//递归fullLine(nums, ans, level + 1);}//放弃元素ans.pop_back();//标志置位未选择flag[i] = false;}}return res;
}

或者设为全局变量

vector<vector<int>> fullLine(const vector<int>& nums,vector<int> ans,int level,\vector<vector<int>>& res,vector<bool> flag){int n = nums.size();for (int i = 0; i <n;i++){if(!flag[i]){//放元素ans.push_back(nums[i]);flag[i] = true;//该元素已选择if(level==3){//不再递归res.push_back(ans);}else{//递归fullLine(nums, ans, level + 1,res,flag);}//放弃元素ans.pop_back();//标志置位未选择flag[i] = false;}}return res;
}

或者:层次大于3时返回结果

vector<vector<int>> res;
vector<bool> flag;
vector<vector<int>> fullLine(const vector<int>& nums,vector<int> ans,int level){int n = nums.size();if(level>3){//结束递归res.push_back(ans);return res;}for (int i = 0; i <n;i++){if(!flag[i]){ans.push_back(nums[i]); //放元素flag[i] = true;//该元素已选择fullLine(nums, ans, level + 1);ans.pop_back(); //放弃元素flag[i] = false; //标志置位未选择}}return res;
}

面试题 08.07. 无重复字符串的排列组合

class Solution {
public:vector<string> permutation(string S) {vector<bool> _flag(S.size(),false);flag=_flag;string str;getPermute(S,str,1);return res;}
private:vector<string> res;vector<bool> flag;//str是一次结果,level是记录层数void getPermute(string S,string str,int level){if(level>S.size()){res.push_back(str);return;//递归结束}for(int i=0;i<S.size();i++){if(!flag[i]){str.push_back(S[i]);flag[i]=true;getPermute(S,str,level+1);str.pop_back();flag[i]=false;}}}
};
  • 可以没有level参数,利用str的大小和S的大小

  • 可以把递归放在for内,但是没有return;

class Solution {
public:vector<string> permutation(string S) {vector<bool> _flag(S.size(),false);flag=_flag;string str;getPermute(S,str);return res;}
private:vector<string> res;vector<bool> flag;//str是一次结果,level是记录层数void getPermute(string S,string str){for(int i=0;i<S.size();i++){if(!flag[i]){str.push_back(S[i]);flag[i]=true;//装结果if(str.size()==S.size()){res.push_back(str);}//递归else{getPermute(S,str);}str.pop_back();flag[i]=false;}}}
};

子集问题

迭代写法

下一层循环的开始值要+1,因为一个元素只能被一层选择

vector<vector<int>> subSet(const vector<int>& nums){vector<vector<int>> res;res.push_back({});//装入空集vector<int> ans;int n = nums.size();for (int i = 0; i < n;i++){ans.push_back(nums[i]);res.push_back(ans);for (int j = i + 1; j < n;j++){//+1ans.push_back(nums[j]);res.push_back(ans);for (int k = j + 1; k < n;k++){//+1ans.push_back(nums[k]);res.push_back(ans);ans.pop_back();}ans.pop_back();}ans.pop_back();}return res;
}
先添加元素再回溯

在这里插入图片描述

注意:前一层选择的元素后一层不能选择,所以下一层的初始值是前一层的i值加一

这里由于i值是递归参数,所以自动递归结束,在i==nums.size()

class Solution {
public:vector<vector<int>> subsets(vector<int>& nums) {vector<int> mm;getSubset(nums,mm,0);//下标从0开始return res;}
private:vector<vector<int>> res;void getSubset(vector<int>& nums,vector<int> ans,int index){res.push_back(ans);int n=nums.size();//if(index==n){//   return;//}for(int i=index;i<n;i++){ans.push_back(nums[i]);//加入元素//回溯getSubset(nums,ans,i+1);//i开始值是i+1//放弃当前选择ans.pop_back();}}
};

或者把res填入ans放入for内,只是要提前放入空集

class Solution {
public:vector<vector<int>> subsets(vector<int>& nums) {res.push_back({});//提前加入空集vector<int> mm;getSubset(nums,mm,0);//下标从0开始return res;}
private:vector<vector<int>> res;void getSubset(vector<int>& nums,vector<int> ans,int index){int n=nums.size();for(int i=index;i<n;i++){ans.push_back(nums[i]);//res.push_back(ans);/*if(index==n-1){}*///回溯//elsegetSubset(nums,ans,i+1);res.push_back(ans);//放在getSubset前后皆可//放弃当前选择ans.pop_back();}}
};
先回溯再加元素

在这里插入图片描述

class Solution {
public:vector<vector<int>> subsets(vector<int>& nums) {vector<int> mm;getSubset(nums,mm,0);return res;}
private:vector<vector<int>> res;void getSubset(vector<int>& nums,vector<int> ans,int index){if(index==nums.size()){res.push_back(ans);return;}//不加入元素getSubset(nums,ans,index+1);//加入元素ans.push_back(nums[index]);getSubset(nums,ans,index+1);//撤销选择ans.pop_back();}
};

总结:

这两种解法实质上是相同的,只是在选择添加子集和进行回溯的时机上有所差异。

  • 第一种解法在每次遍历时都会将当前的子集加入到结果集中
  • 而第二种解法则是在递归结束时才将当前的子集加入到结果集中

两个解法的 index 的含义基本一致,作用不同。

  • 它们都表示后续待选择数组的左边界

    • 解法一index是循环的i+1值

    • 解法二会使用 index 作为判断加入结果集的边界条件。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/2812194.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

git bash:ls查看文件颜色全部为白色的解决方法(已解决)

方法一&#xff1a; 修改~/.bashrc文件或者~/.profile文件&#xff0c;添加如下内容 alias lsls --colorauto 然后 source一下&#xff0c;让修改配置生效 source ~/.profile 然后再ls OK了

vue3+electron开发桌面应用,静态资源处理方式及路径问题总结

1、静态资源放到src/assets/目录下 静态资源,例如图片、静态的JSON文件、视频、CSS等等,放到src/assets目录下。 不然会很蛋疼,这个坑我踩过了。切记,切记!! 以下是CHATGPT-4 Turbo的回答: 在 Vue 应用程序中,src/assets 目录确实有特别的处理。当你使用 Vue CLI 创…

好用的IP反查接口

IP-API.com - Geolocation API - Documentation - JSON 自定义返回参数调用&#xff08;1&#xff09;&#xff1a; http://ip-api.com/json/24.48.0.1?fieldsstatus,message,country,countryCode,region,regionName,cityhttp://ip-api.com/json/24.48.0.1?fieldscountry,co…

<网络安全>《54 概念讲解<第一课 IT和OT>》

1 基本概念 IT&#xff1a;Information Technology的缩写&#xff0c;指信息技术&#xff1b;主要指的是企业中的各个应用系统&#xff0c;包括ERP、MES、EAM、OA等&#xff0c;分布部署在不同的网络层级。除了应用系统&#xff0c;还有计算机&#xff0c;服务器等等&#xff…

input框 自动获取焦点

<el-input style"width:200px" autofocus v-model"leftListname"></el-input> element-ui 的 el-input 组件的 autofocus 属性在某些情况下不能实现自动聚焦,有几个可能的原因: 1. autofocus 在移动设备上不被支持。如果是在移动设备上访问,au…

泽攸科技JS系列高精度台阶仪在半导体领域的应用

泽攸科技JS系列高精度台阶仪是一款先进的自主研发的国产台阶仪&#xff0c;采用了先进的扫描探针技术。通过扫描探针在样品表面上进行微观测量&#xff0c;台阶仪能够准确获取表面形貌信息。其工作原理基于探针与样品表面的相互作用力&#xff0c;通过测量探针的微小位移&#…

【蓝桥杯单片机入门记录】动态数码管

目录 一、数码管动态显示概述 二、动态数码管原理图 &#xff08;1&#xff09;原理图 &#xff08;2&#xff09;动态数码管如何与芯片相连 &#xff08;3&#xff09;“此器件” ——>锁存器74HC573 三、动态数码管显示例程 &#xff08;1&#xff09;例程1&#xf…

Day02:Web架构前后端分离站Docker容器站集成软件站建站分配

目录 常规化站点部署 站库分离 前后端分离 集成软件搭建Web应用 Docker容器搭建Web应用 建立分配站 静态 与 伪静态 总结 章节知识点&#xff1a; 应用架构&#xff1a;Web/APP/云应用/三方服务/负载均衡等 安全产品&#xff1a;CDN/WAF/IDS/IPS/蜜罐/防火墙/杀毒等 渗…

理想滤波器、巴特沃斯滤波器、高斯滤波器实现(包含低通与高通,代码实现与分析)

本篇博客聚焦理想滤波器、巴特沃斯滤波器、高斯滤波器进行原理剖析、代码实现和结果总结&#xff0c;代码含有详细注释&#xff0c;希望帮助大家理解。 以下将从理想低通滤波器、理想高通滤波器、巴特沃斯低通滤波器、巴特沃斯高通滤波器、高斯低通滤波器、高斯高通滤波器六个…

SINAMICS V90 指导手册 第2章 2.2_系统配套表

V90 PN配套表一共有三张&#xff0c;分别是200V低惯量配套表、400V高惯量配套表和400V带直型连接器的配套表。其中200V电压等级低惯量伺服功率范围从0.05-2kW&#xff0c;额定扭矩从0.16-6.37Nm&#xff0c;电缆长度分别是3m、5m、10m、20m四种型号&#xff1b;400V电压等级带直…

【LeetCode】【滑动窗口长度不固定】978 最长湍流子数组

1794.【软件认证】最长的指定瑕疵度的元音子串 这个例题&#xff0c;是滑动窗口中长度不定求最大的题目&#xff0c;在看题之前可以先看一下【leetcode每日一题】【滑动窗口长度不固定】案例。 题目描述 定义&#xff1a;开头和结尾都是元音字母&#xff08;aeiouAEIOU&…

2023年09月CCF-GESP编程能力等级认证Scratch图形化编程一级真题解析

一、单选题&#xff08;共10题&#xff0c;共30分&#xff09; 第1题 我们通常说的“内存”属于计算机部件中的&#xff08; &#xff09;。 A&#xff1a;输出设备 B&#xff1a;输入设备 C&#xff1a;存储设备 D&#xff1a;打印设备 答案&#xff1a;C 第2题 在菜单栏…

Vue:vue的安装与环境的搭建

文章目录 环境搭建安装node.js&#xff08;比较简单&#xff09;安装Vue脚手架初始化启动 环境搭建 安装node.js&#xff08;比较简单&#xff09; 首先要安装node.js&#xff0c;进入官网下载即可。 更改安装路径&#xff0c;保持默认配置&#xff0c;一直点击下一步安装即可…

C语言--- 指针(3)

一.字符指针变量 在指针的类型中&#xff0c;我们知道有一种指针类型为字符指针char * 一般使用&#xff1a; #include<stdio.h> int main() {char ch a;char* p &ch;*p b;printf("%c\n",ch);return 0; } 其实还有一种使用方式 &#xff1a; #inc…

AI云增强升级!还原生动人像,拍出质感照片

近期不少细心用户发现&#xff0c;在用HUAWEI Mate 60 Pro手机拍照后&#xff0c;使用相册中的AI云增强功能&#xff0c;照片变得更加细腻有质感。这是因为AI云增强升级并更新支持了人像模式拍摄的照片&#xff0c;高清自然的人像细节还原和单反级别的光学景深效果&#xff0c;…

高级光线传播与高级外观建模

一.高级光线传播 1、无偏的 ①有偏VS无偏 蒙特卡洛估计出的结果的期望永远是对的 eg&#xff1a;PT中不管有多少样本&#xff0c;期望都是定积分的值 有偏的&#xff1a;估计出的结果的期望和积分的值不一样 一个特殊情况&#xff08;一致的&#xff09;&#xff1a;极限定…

数字电路 第三章—第八节(组合电路中的竞争冒险)

一、竞争冒险的概念及其产生原因 1、竞争冒险的概念 &#xff08;1&#xff09;在组合逻辑电路中&#xff0c;当输入信号改变状态时&#xff0c;输出端可能出现虚假信号——过渡干扰脉冲的现象&#xff0c;叫做竞争冒险。 &#xff08;2&#xff09;如果负载是对脉冲信号十分…

Ubuntu上Jenkins自动化部署Gitee上SpringBoot项目

文章目录 安装安装JDK安装Maven安装GitNodeJS安装&#xff08;可选&#xff09;安装Jenkins 配置Jenkins为Jenkins更换插件源设置jenkins时区安装插件全局工具配置添加Gitee凭证Gitee项目配置 部署后端1.新建任务2.配置源码管理3.构建触发器4.到Gitee中添加WebHook5.构建环境6.…

MATLAB环境下基于分形理论的图像处理研究

分形理论的提出走出了传统整数维度空间的束缚&#xff0c;对物体的描述更加符合自然事物的复杂性与多样性。传统的维度空间是整数的&#xff0c;人们会将空间认为是三维的&#xff0c;平面认定为是二维的&#xff0c;直线是一维的&#xff0c;点被认为是零维的。而这种维度空间…

算法【线性表的查找-顺序查找】

线性表的查找-顺序查找 顺序查找基本思想应用范围顺序表的表示数据元素类型定义查找算法示例分析 时间效率分析顺序查找的特点如何提高查找效率 顺序查找 基本思想 在表的多种结构定义方式中&#xff0c;线性表是最简单的一种。而顺序查找是线性表查找中最简单的一种。 顺序查…