华为机试练习(四)
一、括号匹配
1、
#include<iostream>
#include<string>
#include<cmath>
#include<vector>
using namespace std;
void DeletBract(string str)
{
if(str.length()%2!=0)
cout<<"No"<<endl;
else
{
for(int i=0;i<str.length()-1;i++)
{
if(str[i]=='(')
{
for(int j=i+1;j<str.length();j++)
{
if(str[j]==')')
{
str[i]='a';
str[j]='a';
break;
}
}
}
}
int l=0,r=0;
for(int i=0;i<str.length();i++)
{
if(str[i]==')')
{
l++;
}
else if(str[i]=='(')
{
r++;
}
}
if(l==1)
cout<<"Yes"<<endl;
else if(l==0&&r==0)
cout<<"Yes"<<endl;
else
cout<<"No"<<endl;
}
}
int main()
{
vector<string> vec;
int n;
cin>>n;
fflush(stdin);
for(int i=0;i<n;i++)
{
string str;
getline(cin,str);
vec.push_back(str);
}
for(int i=0;i<n;i++)
{
DeletBract(vec[i]);
}
return 0;
}

#include <bits/stdc++.h>
using namespace std;
const int maxn = 1e5 + 10;
char str[maxn];
stack<char> s;
int main() {
int t;
cin >> t;
while(t--) {
while(!s.empty()) s.pop();
scanf("%s", str);
int n = strlen(str);
if(n == 2) {
if(str[0] == '(' && str[1] == ')') {
puts("No");
continue;
}
}
int i;
int flag1 = 0;
for(i = 0; i < n; i++) {
if(str[i] == '(') {
s.push('(');
} else {
if(!s.empty()) s.pop();
else {
if(flag1) break;
flag1 = 1;
s.push('(');
}
}
}
if(i == n) {
if(!flag1) {
if(s.empty()) puts("Yes");
else puts("No");
}
else {
if(s.size() != 2) puts("No");
else puts("Yes");
}
}
else puts("No");
}
return 0;
}
2、字符串多输入的解决
#include<iostream>
#include<string>
#include<cmath>
#include<vector>
using namespace std;
int main()
{
vector<string> vec;
int n;
string str;
cin>>n;
for(int i=0;i<n;i++)
{
cout<<i<<endl;
getline(cin,str);
vec.push_back(str);
}
for(int i=0;i<vec.size();i++)
{
cout<<vec[i]<<endl;
}
return 0;
}

出现问题,少输入一个字符串。
#include<iostream>
#include<string>
#include<cmath>
#include<vector>
using namespace std;
int main()
{
vector<string> vec;
//int n;
string str;
//cin>>n;
for(int i=0;i<2;i++)
{
cout<<i<<endl;
getline(cin,str);
vec.push_back(str);
}
for(int i=0;i<vec.size();i++)
{
cout<<vec[i]<<endl;
}
return 0;
}

不用n输入值时,可以正常输入,原因可能是之前的cin>>n,会对getline()产生影响。所以出错。
#include<iostream>
#include<vector>
#include<string>
using namespace std;
int main()
{
int NUM;
cout<<"input vetcor size NUM=";
cin>>NUM ;
//getchar();
fflush(stdin); //输入NUM以后缓冲区中有个一个换行,而getline函数不忽略换行,如果不清空,第一个string的内容始终都是换行符
vector<string> str_arr(NUM);
for(int i=0;i<NUM;i++)
{
cout<<"enter the "<<i+1<<" string:";
getline(cin,str_arr[i]);
}
for(int i=0;i<NUM;i++)
cout<<str_arr[i]<<endl;
cout<<endl;
return 0;
}

利用 fflush(stdin);清空缓冲区,getline()才可以正常使用。
3、
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
using namespace std;
int main()
{
string str;
int n;
cin>>n;
vector<string> vec;
for (int i=0;i!=n;i++)
{
cin>>str;
vec.push_back(str);
}
for (int j=0;j!=n;j++)
{
reverse(vec[j].begin(),vec[j].end()); //vec[i]在string中是该字符串的对象,也是首地址
}
for (int j=0;j!=n;j++)
{
cout<<vec[j]<<endl;
cout<<vec[j][0]<<endl; //相当于str[i] 数组的某一个元素
}
return 0;
}

利用cin可以多次输入。利用vector容器可以形成二维数组。
3、
#include<iostream>
#include<string>
#include<cmath>
#include<vector>
using namespace std;
void DeletBract(string str)
{
if(str.length()%2!=0)
cout<<"No"<<endl;
else
{
for(int i=0;i<str.length()-1;i++)
{
if(str[i]=='(')
{
for(int j=i+1;j<str.length();j++)
{
if(str[j]==')')
{
str[i]='a';
str[j]='a';
break;
}
}
}
}
int l=0,r=0;
for(int i=0;i<str.length();i++)
{
if(str[i]==')')
{
l++;
}
else if(str[i]=='(')
{
r++;
}
}
if(l==1||l==0)
cout<<"Yes"<<endl;
else
cout<<"No"<<endl;
}
}
int main()
{
vector<string> vec;
int n;
cin>>n;
fflush(stdin);
for(int i=0;i<n;i++)
{
string str;
getline(cin,str);
vec.push_back(str);
}
for(int i=0;i<n;i++)
{
DeletBract(vec[i]);
}
return 0;
}

二、stack应用
1、
#include <stack>
#include <iostream>
using namespace std;
int main()
{
// 创建堆栈对象
stack<int> s;
// 元素入栈
s.push(3);
s.push(19);
s.push(23);
s.push(36);
s.push(50);
s.push(4);
cout<<"stack size is:"<<s.size()<<endl;
// 元素依次出栈
while(!s.empty())
{
// 打印栈顶元素,打印出:4 50 36 23 19 3
cout << s.top() << endl;
// 出栈
s.pop();
}
return 0;
}

三、
输入描述:
输入第一行为一个正整数n(1≤n≤1000),下面n行为n个字符串(字符串长度≤100),字符串中只含有大小写字母。
输出描述:
数据输出n行,输出结果为按照字典序排列的字符串。
1、
#include<iostream>
#include<vector>
#include<string>
#include<algorithm>
using namespace std;
int main()
{
int n;
cin>>n;
vector<string> vec;
while(n)
{
string str;
cin>>str;
vec.push_back(str);
n--;
}
sort(vec.begin(),vec.end());
vector<string>::iterator it;
for(it=vec.begin();it!=vec.end();it++)
{
cout<<*it<<endl;
}
return 0;
}
利用 vector 和algorithm来做。
2、sort 函数
#include <iostream>
#include <algorithm>
using namespace std;
int main()
{
int a[20]={2,2,1,23,5,76,0,43,24,65},i;
for(i=0;i<10;i++)
cout<<a[i]<<" ";
cout<<endl;
sort(a,a+10);
for(i=0;i<10;i++)
cout<<a[i]<<" ";
return 0;
}

3、
#include<iostream>
#include<set>
#include<string>
#include<algorithm>
using namespace std;
int main()
{
int n;
cin>>n;
set<string> vec;
while(n)
{
string str;
cin>>str;
vec.insert(str);
n--;
}
//sort(vec.begin(),vec.end());
set<string>::iterator it;
for(it=vec.begin();it!=vec.end();it++)
{
cout<<*it<<endl;
}
return 0;
}

四、
输入一个int型的正整数,计算出该int型数据在内存中存储时1的个数。
输入描述:
输入一个整数(int类型)
输出描述:
这个数转换成2进制后,输出1的个数
1、
#include<iostream>
using namespace std;
int main()
{
int t;
cin>>t;
int count=0;
while(t>0)
{
if(t%2)count++;
t=t/2;
}
cout<<count<<endl;
}

2、位运算
#include<iostream>
using namespace std;
int main()
{
int a;
while(cin>>a)
{
int count=0;
while(a)
{
if((a&1)>0)//和1位运算,都是1,取1
count++;//判断二进制有多少个1
a=a>>1;//右移1位,相当于除以2;
cout<<a<<endl;
}
cout<<count<<endl;
}
return 0;
}


四、
题目描述
开发一个坐标计算工具, A表示向左移动,D表示向右移动,W表示向上移动,S表示向下移动。从(0,0)点开始移动,从输入字符串里面读取一些坐标,并将最终输入结果输出到输出文件里面。
输入:
合法坐标为A(或者D或者W或者S) + 数字(两位以内)
坐标之间以;分隔。
非法坐标点需要进行丢弃。如AA10; A1A; $%$; YAD; 等。
输入
A10;S20;W10;D30;X;A1A;B10A11;;A10;
输出
10,-10
1、
容易搞混的两个函数,给出所有重载函数:
int find(char c, int pos = 0) const;//从pos开始查找字符c在当前字符串的位置
int find(const char *s, int pos = 0) const;//从pos开始查找字符串s在当前串中的位置
int find(const char *s, int pos, int n) const;//从pos开始查找字符串s中前n个字符在当前串中的位置
int find(const string &s, int pos = 0) const;//从pos开始查找字符串s在当前串中的位置
int find_first_of(char c, int pos = 0) const;//从pos开始查找字符c第一次出现的位置
int find_first_of(const char *s, int pos = 0) const; //从pos开始查找当前串中第一个在s的前n个字符组成的数组里的字符的位置
int find_first_of(const char *s, int pos, int n) const;
int find_first_of(const string &s,int pos = 0) const;
共同点:
查找成功时返回所在位置,失败返回string::npos的值,string::npos一般是MAX_INT(即2^32 - 1)
差异:
find(): 查找字符串中第一次出现字符c、字符串s的位置;
find_first_of(): 查找字符串中字符c、字符数组s中任意一个字符第一次出现的位置。
#include<iostream>
using namespace std;
int main()
{
string haystack = "helloworld";
string needle = "world";
cout << haystack.find_first_of(needle) << endl; //2, index of first 'l' ,needle任意一个字符第一次出现的位置
cout << haystack.find(needle) << endl; //5, index of first "world" ,world 第一次出现的位置
needle = "";
cout << haystack.find_first_of(needle) << endl;//string::npos, 因为字符数组s为空,haystack中找不到空字符(区别于'\0')
cout << haystack.find(needle) << endl;//0, 空串
}

2、
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str;
while(getline(cin,str))
{
pair<int,int> point(0,0);//不需要等于号 ,记录坐标
int index,start=0;//找到;的位置
string s;
index=str.find_first_of(";");
while(index!=string::npos)
{
s=str.substr(start,index-start);//注意是差值,是个数而非下标
cout<<s<<endl;
start=index+1;
index=str.find_first_of(";",index+1);
}
//A10;S20;W10;D30;X;A1A;B10A11;;A10;
}
}

利用 string.find_first_of()查找;的下标,利用substr获取字符串。
3、
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str;
while(getline(cin,str))
{
pair<int,int> point(0,0);//不需要等于号 ,记录坐标
int index=str.find_first_of(";");
int start=0;//找到;的位置
while(index!=string::npos)
{
string s=str.substr(start,index-start);//注意是差值,是个数而非下标
start=index+1;
index=str.find_first_of(";",index+1);
if(s.size()>1&&s.size()<=3)//只能有2或者3个字符
{
int num=0,flag=0;
for(int i=1;i<s.size();i++)//注意是s.size
{
if(s[i]>='0'&&s[i]<='9')
{
num=num*10+(s[i]-'0');
}
else
{
flag=1;
break;
}
}
if(flag==0)
{
switch(s[0])
{
case 'A':
{
point.first=point.first-num;
break;
}
case 'D':
{
point.first=point.first+num;
break;
}
case 'W':
{
point.second=point.second+num;
break;
}
case 'S':
{
point.second=point.second-num;
break;
}
}
}
}
}
cout<<point.first<<","<<point.second<<endl;
}
return 0;
}//A10;S20;W10;D30;X;A1A;B10A11;;A10;

4、switch 理论上不加break没影响,但是
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str;
while(getline(cin,str))
{
pair<int,int> point(0,0);//不需要等于号 ,记录坐标
int index=str.find_first_of(";");
int start=0;//找到;的位置
while(index!=string::npos)
{
string s=str.substr(start,index-start);//注意是差值,是个数而非下标
start=index+1;
index=str.find_first_of(";",index+1);
if(s.size()>1&&s.size()<=3)//只能有2或者3个字符
{
int num=0,flag=0;
for(int i=1;i<s.size();i++)//注意是s.size
{
if(s[i]>='0'&&s[i]<='9')
{
num=num*10+(s[i]-'0');
}
else
{
flag=1;
break;
}
}
if(flag==0)
{
switch(s[0])
{
case 'A':
{
point.first=point.first-num;
//break;
}
case 'D':
{
point.first=point.first+num;
//break;
}
case 'W':
{
point.second=point.second+num;
//break;
}
case 'S':
{
point.second=point.second-num;
//break;
}
}
}
}
}
cout<<point.first<<","<<point.second<<endl;
}
return 0;
}//A10;S20;W10;D30;X;A1A;B10A11;;A10;

却出错。
通过调试,发现case A 和case W 会相互影响。

所以以后碰到case记住加break。或者直接用if判断。
5、
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str;
while(getline(cin,str))
{
pair<int,int> point(0,0);//不需要等于号 ,记录坐标
int index=str.find_first_of(";");
int start=0;//找到;的位置
while(index!=string::npos)
{
string s=str.substr(start,index-start);//注意是差值,是个数而非下标
start=index+1;
index=str.find_first_of(";",index+1);
if(s.size()>1&&s.size()<=3)//只能有2或者3个字符
{
int num=0,flag=0;
for(int i=1;i<s.size();i++)//注意是s.size
{
if(s[i]>='0'&&s[i]<='9')
{
num=num*10+(s[i]-'0');
}
else
{
flag=1;
break;
}
}
if(flag==0)
{
if(s[0]=='A')
{
point.first=point.first-num;
//break;
}
else if(s[0]=='D')
{
point.first=point.first+num;
//break;
}
else if(s[0]=='W')
{
point.second=point.second+num;
//break;
}
else if(s[0]=='S')
{
point.second=point.second-num;
//break;
}
}
}
}
cout<<point.first<<","<<point.second<<endl;
}
return 0;
}//A10;S20;W10;D30;X;A1A;B10A11;;A10; A10;D20;W10;S20;

6、用结构体struct 表示
#include<iostream>
#include<string>
using namespace std;
struct Point //定义结构体
{
int x;
int y;
} ;
int main()
{
string str;
while(getline(cin,str))
{
Point p[1];//不需要等于号 ,记录坐标
p[0].x=0;
p[0].y=0;
int index=str.find_first_of(";");
int start=0;//找到;的位置
while(index!=string::npos)
{
string s=str.substr(start,index-start);//注意是差值,是个数而非下标
start=index+1;
index=str.find_first_of(";",index+1);
if(s.size()>1&&s.size()<=3)//只能有2或者3个字符
{
int num=0,flag=0;
for(int i=1;i<s.size();i++)//注意是s.size
{
if(s[i]>='0'&&s[i]<='9')
{
num=num*10+(s[i]-'0');
}
else
{
flag=1;
break;
}
}
if(flag==0)
{
if(s[0]=='A')
{
p[0].x-=num;
//break;
}
else if(s[0]=='D')
{
p[0].x+=num;
//break;
}
else if(s[0]=='W')
{
p[0].y+=num;
//break;
}
else if(s[0]=='S')
{
p[0].y-=num;
//break;
}
}
}
}
cout<<p[0].x<<","<<p[0].y<<endl;
}
return 0;
}//A10;S20;W10;D30;X;A1A;B10A11;;A10; A10;D20;W10;S20;

五、
他是这么变换的,大家都知道手机上的字母: 1--1, abc--2, def--3, ghi--4, jkl--5, mno--6, pqrs--7, tuv--8 wxyz--9, 0--0,就这么简单,渊子把密码中出现的小写字母都变成对应的数字,数字和其他的符号都不做变换,
声明:密码中没有空格,而密码中出现的大写字母则变成小写之后往后移一位,如:X,先变成小写,再往后移一位,不就是y了嘛,简单吧。记住,z往后移是a哦。
输入描述:
输入包括多个测试数据。输入是一个明文,密码长度不超过100个字符,输入直到文件结尾
输出描述:
输出渊子真正的密文
输入
YUANzhi1987
输出
zvbo9441987
1、
#include<iostream>
#include<string>
using namespace std;
const string dict1="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
const string dict2="bcdefghijklmnopqrstuvwxyza22233344455566677778889999";
char Char_Change(char a){
for(int i=0;i<dict1.size();i++)
if(dict1[i]==a) return dict2[i];
return a;
}
int main(){
//string data="YUANzhi1987";
string data;
while(getline(cin,data)){
for(int i=0;i<data.size();i++)
data[i] = Char_Change(data[i]);
cout<<data<<endl;
}
return 0;
}
牛客网上的程序,将对应输出先用静态变量表示出来,。注意这里定义函数的返回,多个return时,返回最先满足条件的。
2、
#include<iostream>
#include<string>
using namespace std;
const string str_1="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
const string str_2="bcdefghijklmnopqrstuvwxyza22233344455566677778889999";
char Char_change(char a)
{
int flag=0;
for(int i=0;i<str_1.size();i++)
{
if(str_1[i]==a)
{
return str_2[i];
flag=1;
}
}
if(flag==0)//注意,最好别用判断输出,牛客网通不过
{
return a;
}
}
int main()
{
string str;
while(getline(cin,str))
{
for(int i=0;i<str.size();i++)
{
cout<<Char_change(str[i]);
}
}
return 0;
}

3、以上程序通过循环获取对应位置,也可以通过find函数
#include<iostream>
#include<string>
using namespace std;
const string str_1="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
const string str_2="bcdefghijklmnopqrstuvwxyza22233344455566677778889999";
char Char_change(char a)
{
int index;
index=str_1.find(a);
if(index>=0)
return str_2[index];
return a;
}
int main()
{
string str;
while(getline(cin,str))
{
for(int i=0;i<str.size();i++)
{
cout<<Char_change(str[i]);
}
}
return 0;
}//YUANzhi1987

4、
#include<iostream>
#include<string>
using namespace std;
const string str_1="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
const string str_2="bcdefghijklmnopqrstuvwxyza22233344455566677778889999";
char Char_change(char a)
{
int index;
index=str_1.find(a);
if(index>=0)
return str_2[index];
else
{
return a;
}
}
int main()
{
string str;
while(getline(cin,str))
{
for(int i=0;i<str.size();i++)
{
cout<<Char_change(str[i]);
}
}
return 0;
}//YUANzhi1987
这次的判断返回,可以通过牛客网测试
六、
密码要求:
1.长度超过8位 2.包括大小写字母.数字.其它符号,以上四种至少三种 3.不能有相同长度超2的子串重复
说明:长度超过2的子串
输入描述:
一组或多组长度超过2的子符串。每组占一行
输出描述:
如果符合要求输出:OK,否则输出NG
输入
021Abc9000 021Abc9Abc1 021ABC9000 021$bc9000
输出
OK NG NG OK
1、
#include <iostream>
#include <string>
using namespace std;
int main()
{
string str;
while(cin >> str)
{
int flag[4] = {0};
if(str.size() <= 8)
goto NG;
for(int i = 0; i < str.size(); ++i)//四种情况统计
if(str[i] >= 'a' && str[i] <= 'z')
flag[0] = 1;
else if(str[i] >= 'A' && str[i] <= 'Z')
flag[1] = 1;
else if(str[i] >= '0' && str[i] <= '9')
flag[2] = 1;
else
flag[3] = 1;
if(flag[0] + flag[1] + flag[2] + flag[3] < 3)
goto NG;
for(int i = 0; i <= str.size()-6; i++)//长度超过二的统计
for(int j = i+3;j < str.size();j++)
if(str[i] == str[j] && str[i+1] == str[j+1] &&str[i+2] == str[j+2])
goto NG;
OK:
cout << "OK" << endl;continue;
NG:
cout << "NG" << endl;
}
return 0;
}

学习goto的应用。再有注意他们判断的逻辑。
2、判断大于2个重复的字符串
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str="021Abc9Abc000";
for(int i=0;i<str.size()-6;i++)//判断大于2个重复子串,只要有大于等于3的子串就可以
{
for(int j=i+3;j<str.size();j++)
{
if(str[i]==str[j]&&str[i+1]==str[j+1]&&str[i+2]==str[j+2])
{
cout<<"有长度大于2的重复子串";
break;
}
}
}
return 0;
}

3、
#include<iostream>
#include<string>
using namespace std;
int main()
{
string str;
while(getline(cin,str))
{
int flag=0;//标记
int s=0;
if(str.size()>8)
{
for(int i=0;i<str.size()-6;i++)//判断大于2个重复子串,只要有大于等于3的子串就可以
{
for(int j=i+3;j<str.size();j++)
{
if(str[i]==str[j]&&str[i+1]==str[j+1]&&str[i+2]==str[j+2])//说明有大于2的字符串
{
flag=1;
break;
}
}
}
for(int i=0;i<str.size();i++) //四种符号判断
{
if(str[i]>='a'&&str[i]<='z')
{
s++;
}
else if(str[i]>='A'&&str[i]<='Z')
{
s++;
}
else if(str[i]>='1'&&str[i]<='9')
{
s++;
}
else
{
s++;
}
}
if(s<3)
{
flag=1;
}
}
if(flag==0)
{
cout<<"OK"<<endl;
}
else if(flag==1)
{
cout<<"NG"<<endl;
}
}
return 0;
}

这是利用flag形式最终判断的程序,比较繁琐,并且多了很多无用的判断。利用goto,只要一不符合条件就可以跳出判断到最后。
七、
开发一个简单错误记录功能小模块,能够记录出错的代码所在的文件名称和行号。
处理:
1、 记录最多8条错误记录,循环记录,对相同的错误记录(净文件名称和行号完全匹配)只记录一条,错误计数增加;
2、 超过16个字符的文件名称,只记录文件的最后有效16个字符;
3、 输入的文件可能带路径,记录文件名称不能带路径。
输入描述:
一行或多行字符串。每行包括带路径文件名称,行号,以空格隔开。
输出描述:
将所有的记录统计并将结果输出,格式:文件名 代码行数 数目,一个空格隔开,如:
输入
E:\V1R2\product\fpgadrive.c 1325
输出
fpgadrive.c 1325 1
1、
#include <iostream>
#include <string>
#include<cstring>
#include<algorithm>
using namespace std;
int main()
{
string str="E:/V1R2\product\fpgadrive.c";
cout<<str.length()<<endl;
for(int i=0;i<str.length();i++)
cout<<str[i]<<" ";
cout<<endl;
int pos = str.rfind('e');
cout<<pos<<endl;
}

可以看出识别不了直接写入的字符创中的反斜杠
#include <iostream>
#include <string>
#include<cstring>
#include<algorithm>
using namespace std;
int main()
{
string str,s;
cin>>str;
cout<<str.length()<<endl;
for(int i=0;i<str.length();i++)
cout<<str[i]<<" ";
cout<<endl;
int pos = str.rfind('\\'); //注意双斜杠识别反斜杠
cout<<pos<<endl;
s=str.substr(pos+1);
cout<<s<<endl;
}//="E:/V1R2\product\fpgadrive.c"

但是这样输入的字符串可以识别,可以找出最后的文件名。rfind,逆序查找某一字符第一次出现的位置。
2、
#include<iostream>
#include<vector>
#include<string>
using namespace std;
struct Eorr //定义结构体
{
string path;
int col;
int num=1;
};
int main()
{
vector<Eorr> vec; //vector容器
Eorr infor;
for(int i=0;i<3;i++)
{
cin>>infor.path>>infor.col;
vec.push_back(infor); //容器添加内容
}
cout<<vec.size()<<endl;
int index;
for(int i=0;i<vec.size();i++)
{
if(vec[i].col==641)
cout<<i<<endl;
}
} //G:\rp\onajqj\maahmq 631 E:\njfgjkcrh 641 C:\co\zk\ao\bxgxjfgrwckfxekeqro 629
利用结构体和vector可以比较,定位位置

641在下标为1的位置。
3、
#include<iostream>
#include<vector>
#include<string>
using namespace std;
const int NUM=1;
struct Eorr //定义结构体
{
string path;
int col;
int num;
};
string Getfilename(string s)//得到文件名字
{
string name;
int n;
n=s.rfind('\\');//逆序查找反斜杠
name=s.substr(n+1);
if(name.size()>4)
name=name.substr(name.size()-4);
return name;
}
int main()
{
vector<Eorr> vec; //vector容器
string filepath;
int Col;
int Num=1;
cin>>filepath;
cin>>Col;
Eorr infor;
infor.path=Getfilename(filepath);
infor.col=Col;
infor.num=NUM;
vec.push_back(infor);
for(int j=0;j<3;j++)
{
int flag=0;
cin>>filepath;
cin>>Col;
infor.path=Getfilename(filepath);
infor.col=Col;
infor.num=NUM;
for(int i=0;i<vec.size();i++)
{
if(vec[i].path==infor.path&&vec[i].col==infor.col)
{
vec[i].num++; //容器添加内容
flag=1;
break;
}
}
if(flag==0)
{
vec.push_back(infor);
}
flag=0;
}
for(int i=0;i<vec.size();i++)
{
cout<<vec[i].path<<" "<<vec[i].col<<" "<<vec[i].num<<endl;
}
return 0;
} //G:\rp\onajqj\maahmq 631 E:\njfgjkcrh 641 C:\co\zk\ao\bxgxjfgrwckfxekeqro 629 G:\rp\onajqj\maahmq 631

用四个测试;通过循环读取比测判断个数的。
4、
#include<iostream>
#include<vector>
#include<string>
using namespace std;
const int NUM=1;
struct Eorr //定义结构体
{
string path;
int col;
int num;
};
string Getfilename(string s)//得到文件名字
{
string name;
int n;
n=s.rfind('\\');//逆序查找反斜杠
name=s.substr(n+1);
if(name.size()>4)
name=name.substr(name.size()-4);
return name;
}
int main()
{
vector<Eorr> vec; //vector容器
string filepath;
int Col;
int Num=1;
cin>>filepath;
cin>>Col;
Eorr infor;
infor.path=Getfilename(filepath);
infor.col=Col;
infor.num=NUM;
vec.push_back(infor);
while(cin>>filepath>>Col)
{
int flag=0;
//cin>>filepath;
//cin>>Col;
infor.path=Getfilename(filepath);
infor.col=Col;
infor.num=NUM;
for(int i=0;i<vec.size();i++)
{
if(vec[i].path==infor.path&&vec[i].col==infor.col)
{
vec[i].num++; //容器添加内容
flag=1;
break;
}
}
if(flag==0)
{
vec.push_back(infor);
}
flag=0;
}
for(int i=0;i<vec.size();i++)
{
cout<<vec[i].path<<" "<<vec[i].col<<" "<<vec[i].num<<endl;
}
return 0;
} //G:\rp\onajqj\maahmq 631 E:\njfgjkcrh 641 C:\co\zk\ao\bxgxjfgrwckfxekeqro 629 G:\rp\onajqj\maahmq 631

while 循环输入,输出的结果,只需要将最后八个输出即可;

5、
最终程序
#include<iostream>
#include<vector>
#include<string>
using namespace std;
const int NUM=1;
struct Eorr //定义结构体
{
string path;
int col;
int num;
};
string Getfilename(string s)//得到文件名字
{
string name;
int n;
n=s.rfind('\\');//逆序查找反斜杠
name=s.substr(n+1);
if(name.size()>16)
name=name.substr(name.size()-16);
return name;
}
int main()
{
vector<Eorr> vec; //vector容器
string filepath;
int Col;
int Num=1;
cin>>filepath;
cin>>Col;
Eorr infor;
infor.path=Getfilename(filepath);
infor.col=Col;
infor.num=NUM;
vec.push_back(infor);//第一个vector
while(cin>>filepath>>Col)//循环输入
{
int flag=0;
//cin>>filepath;
//cin>>Col;
infor.path=Getfilename(filepath);
infor.col=Col;
infor.num=NUM;
for(int i=0;i<vec.size();i++)
{
if(vec[i].path==infor.path&&vec[i].col==infor.col)
{
vec[i].num++; //容器添加内容
flag=1;
break;
}
}
if(flag==0)
{
vec.push_back(infor);
}
flag=0;
}
if(vec.size()>8)//循环输出
{
for(int i=vec.size()-8;i<vec.size();i++)
{
cout<<vec[i].path<<" "<<vec[i].col<<" "<<vec[i].num<<endl;
}
}
else
{
for(int i=0;i<vec.size();i++)
{
cout<<vec[i].path<<" "<<vec[i].col<<" "<<vec[i].num<<endl;
}
}
return 0;
} //G:\rp\onajqj\maahmq 631 E:\njfgjkcrh 641 C:\co\zk\ao\bxgxjfgrwckfxekeqro 629 G:\rp\onajqj\maahmq 631
6、
vector 中find函数
#include <iostream>
#include<algorithm>
#include<vector>
using namespace std;
struct error_codes
{
string filename;
int codeline;
int counter=1;
bool operator==(const error_codes &a)//运算符比较的重载
{
if(a.filename==filename&&a.codeline==codeline)
return true;
else
return false;
}
};
string getfilename(string f) //从地址字符串中,获取最后的文件名
{
char *fronts,*backs;
fronts=&f[0];
backs=&f[0];
while(*fronts!='\0')
{
if(*fronts=='\\')
{
backs=fronts;
}
++fronts;
}
string result;
++backs;
if(*fronts=='\0')
{
while(fronts!=backs)
{
result=result+*backs;
++backs;
}
backs+='\0';
}
if(result.size()>16)
result=result.substr(result.size()-16,16);
return result;
}
int main()
{
vector<error_codes> inputnumber;
string filename;
int codeline=0;
int i=0;//输入的次数
while(cin>>filename>>codeline)//输入
{
error_codes temp;//结构体
temp.filename=getfilename(filename);//名字
temp.codeline=codeline;//行号
vector<error_codes>::iterator res;//迭代器
res=find(inputnumber.begin(),inputnumber.end(),temp);
if(res==inputnumber.end()) //temp不在inpunumber数组中
{
inputnumber.push_back(temp);//将结构体加入到vector中
}
else
{
res->counter++;//有的话count+1;
}
++i;
}
int j=0;//所有都记录,只输出最后8个
if(inputnumber.size()>8)
j=inputnumber.size()-8;
for(j;j<inputnumber.size();++j)
{
cout<<inputnumber[j].filename<<" "<<inputnumber[j].codeline<<" "<<inputnumber[j].counter<<endl;
}
return 0;
}
该find方法需要运算符的比较重载
7、
测试用例:可以看到是记录所有的,只输出最后8个。
G:\rp\onajqj\maahmq 631
E:\njfgjkcrh 641
C:\co\zk\ao\bxgxjfgrwckfxekeqro 629
D:\mf\si\jmfdahkeffyjjsf 646
E:\wn\arefkiz 633
C:\gpjleb\cinhhx\zjydgr\njfgjkcrh 640
E:\nwrrhx\qyw\bxgxjfgrwckfxekeqro 636
G:\usgsl\ywr\tve\cqekvaxypemktyurn 647
C:\jftbig\arefkiz 650
F:\rgk\cai\arefkiz 640
D:\tvse\vs\dhzrmy\njfgjkcrh 634
E:\coba\qbs\xagq\njfgjkcrh 628
F:\wnfsmf\oxrvbv\njfgjkcrh 632
C:\khqx\nv\jmfdahkeffyjjsf 637 F:\hm\ra\uaxckn\bxgxjfgrwckfxekeqro 647 D:\soq\jmfdahkeffyjjsf 642 F:\moxnw\szxcdhlaytgj 639 E:\avcop\jd\vwtrt\njfgjkcrh 650 E:\hou\vv\szxcdhlaytgj 631 C:\uozkwd\bxgxjfgrwckfxekeqro 650 F:\jmfdahkeffyjjsf 650
E:\hgoxms\nwax\szxcdhlaytgj 633 F:\vylww\zhh\cqekvaxypemktyurn 643 C:\njfgjkcrh 637 F:\bfn\dxwjje\jmfdahkeffyjjsf 632 E:\bxgxjfgrwckfxekeqro 634 G:\gwuusj\ized\qq\szxcdhlaytgj 646 F:\arefkiz 644 G:\zsw\uewu\arefkiz 634 E:\ja\zg\njfgjkcrh 644
D:\gfute\ju\wuy\szxcdhlaytgj 636 C:\mpgcx\kcgi\arefkiz 645 C:\zayn\jmfdahkeffyjjsf 648 F:\kkplu\avvw\hbzmwj\jmfdahkeffyjjsf 648 E:\maahmq 631 E:\hs\xnto\jmfdahkeffyjjsf 645
G:\cqekvaxypemktyurn 633
D:\maahmq 646
E:\jmfdahkeffyjjsf 636
G:\hbvm\szxcdhlaytgj 642 对应输出应该为: szxcdhlaytgj 636 1 arefkiz 645 1 jmfdahkeffyjjsf 648 2 jmfdahkeffyjjsf 645 1 qekvaxypemktyurn 633 1 maahmq 646 1 jmfdahkeffyjjsf 636 1 szxcdhlaytgj 642 1
八、
题目描述
请解析IP地址和对应的掩码,进行分类识别。要求按照A/B/C/D/E类地址归类,不合法的地址和掩码单独归类。
所有的IP地址划分为 A,B,C,D,E五类
A类地址1.0.0.0~126.255.255.255;
B类地址128.0.0.0~191.255.255.255;
C类地址192.0.0.0~223.255.255.255;
D类地址224.0.0.0~239.255.255.255;
E类地址240.0.0.0~255.255.255.255
私网IP范围是:10.0.0.0~10.255.255.255 172.16.0.0~172.31.255.255 192.168.0.0~192.168.255.255
输入描述:
多行字符串。每行一个IP地址和掩码,用~隔开。
输出描述:
统计A、B、C、D、E、错误IP地址或错误掩码、私有IP的个数,之间以空格隔开。
输入
10.70.44.68~255.254.255.0 1.0.0.1~255.0.0.0 192.168.0.2~255.255.255.0 19..0.~255.255.255.0
输出
1 0 1 0 0 2 1
1、
获取字符串
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
int main()
{
string str= "10.70.44.68";
vector<int> vec;
string s(str.begin(),str.end()-3);
string t=str.substr(0,2);
cout<<s<<endl;
cout<<t;
}

可以通过这种方法不用循环,获取字符串中间的子串,同理也可以通过substr获取。
2、拆分点,获取每一个数值
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
int main()
{
string str= "10.70.44.68";
vector<int> vec;
for(int i=0;i<str.length();i++)
{
int j=i;
for(;j<=str.size();j++)
{
if(str[j]=='.'||j==str.size())
{
string s(str.begin()+i,str.begin()+j);//获取子串的方式
int num=atoi(s.c_str());//atoi将char变为int,c_str将string变为char
vec.push_back(num);
break;
}
}
i=j;
}
cout<<endl;
for(int i=0;i<vec.size();i++)
cout<<vec[i]<<" ";
}

3、返回vector中的值,要么用全局变量,要么用指针
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
// 初步判断输入的点十分进制表示法是否正确
void isValie(string str,vector<int> &vec)//添加指针
{
for(int i=0;i<str.length();i++)
{
int j=i;
for(;j<=str.size();j++)
{
if(str[j]=='.'||j==str.size())
{
string s(str.begin()+i,str.begin()+j);//获取子串的方式
int num=atoi(s.c_str());//atoi将char变为int,c_str将string变为char
vec.push_back(num);
break;
}
}
i=j;
}
}
int main()
{
string str= "10.70.44.68";
vector<int> vec;
isValie(str,vec);
for(int i=0;i<vec.size();i++)
cout<<vec[i]<<" ";
}
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
// 初步判断输入的点十分进制表示法是否正确
vector<int> vec;
void isValie(string str)//添加指针
{
for(int i=0;i<str.length();i++)
{
int j=i;
for(;j<=str.size();j++)
{
if(str[j]=='.'||j==str.size())
{
string s(str.begin()+i,str.begin()+j);//获取子串的方式
int num=atoi(s.c_str());//atoi将char变为int,c_str将string变为char
vec.push_back(num);
break;
}
}
i=j;
}
}
int main()
{
string str= "10.70.44.68";
isValie(str);
for(int i=0;i<vec.size();i++)
cout<<vec[i]<<" ";
}
两种结果是一样的,但是指针类型可以循环处理多组数据,全局变量的话需要多次置零。
但是注意输入这样的ip后 10..44.68,出现如下结果,注意不输入的情况。

4、
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
bool IpValid(string str,vector<int> &vec)//添加指针,将各个数摘出来
{
for(int i=0;i<str.length();i++)
{
int j=i;
for(;j<=str.size();j++)
{
if(str[j]=='.'||j==str.size())
{
string s(str.begin()+i,str.begin()+j);//获取子串的方式
if(s.size()==0) //10..44.68避免这样情况
return false;
int num=atoi(s.c_str());//atoi将char变为int,c_str将string变为char
vec.push_back(num);
break;
}
}
i=j;
}
if(vec.size()!=4)//个数判断
return false;
for(int i=0;i<vec.size();i++)
{
if(vec[i]<0||vec[i]>255)//范围判断
return false;
}
return true;
}
void NumtoVec(int num,vector<int> &box)//逆序存放,将数字转为8位的二进制存放
{ //形参中添加vector,是想将数字从函数内传递传去
vector<int> box1;
int n;
int m=0;
while(num>=0 && m<8)
{
n=num%2;
box1.push_back(n);
num=num/2;
m++;
}
for(int i=0;i<box1.size();i++)//逆序变正
{
box.push_back(box1[box1.size()-i-1]);
}
}
bool MaskValid(string str)
{
vector<int> vec;
vector<int> box;
if(IpValid(str,vec)==false) //不满足则退出
return false;
for(int i=0;i<vec.size();i++)
cout<<vec[i]<<" ";
cout<<endl;
for(int i=0;i<vec.size();i++)
{
NumtoVec(vec[i],box);
}
for(int i=0;i<box.size();i++)
cout<<box[i]<<" ";
}
int main()
{
string str= "10.70.44.68~255.254.255.0";
//string str= "10.70.44.68~5.4.2.0";
vector<int> vec;
string str_ip,str_mask;
int n=str.find('~');
str_ip=str.substr(0,11);
str_mask=str.substr(n+1,str.size());
IpValid(str_ip,vec);
for(int i=0;i<vec.size();i++)
cout<<vec[i]<<" ";
cout<<endl;
MaskValid(str_mask);
}

5、
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
bool IpValid(string str,vector<int> &vec)//添加指针,将各个数摘出来
{
for(int i=0;i<str.length();i++)
{
int j=i;
for(;j<=str.size();j++)
{
if(str[j]=='.'||j==str.size())
{
string s(str.begin()+i,str.begin()+j);//获取子串的方式
if(s.size()==0) //10..44.68避免这样情况
return false;
int num=atoi(s.c_str());//atoi将char变为int,c_str将string变为char
vec.push_back(num);
break;
}
}
i=j;
}
if(vec.size()!=4)//个数判断
return false;
for(int i=0;i<vec.size();i++)
{
if(vec[i]<0||vec[i]>255)//范围判断
return false;
}
return true;
}
void NumtoVec(int num,vector<int> &box)//逆序存放,将数字转为8位的二进制存放
{ //形参中添加vector,是想将数字从函数内传递传去
vector<int> box1;
int n;
int m=0;
while(num>=0 && m<8)
{
n=num%2;
box1.push_back(n);
num=num/2;
m++;
}
for(int i=0;i<box1.size();i++)//逆序变正
{
box.push_back(box1[box1.size()-i-1]);//255.255.255.0 --> 1111111111111111111111110000000
}
}
bool MaskValid(string str)
{
vector<int> vec;
vector<int> box;
if(IpValid(str,vec)==false) //不满足则退出
return false;
for(int i=0;i<vec.size();i++)
{
NumtoVec(vec[i],box);
}
for(int i=0;i<box.size();i++)
cout<<box[i];
cout<<endl;
int n=box.size(),m=-1;//1逆序查找,0正序查找,如果1的下标大于0,说明不符合
for(int i=0;i<box.size();i++)
{
if(box[i]==0)
{
n=i;
break;
}
}
for(int i=box.size()-1;i>=0;i--)
{
if(box[i]==1)
{
m=i;
break;
}
}
if(n==box.size()||m==-1)//这是为了出现0.0.0.0或者255.255.255.255特殊情况
return false;
else if(n<m)
return false;
else
return true;
}
int main()
{
//string str= "10.70.44.68~255.255.255.0";
string str= "10.70.44.68~5.4.2.0";
vector<int> vec;
string str_ip,str_mask;
int n=str.find('~');
str_ip=str.substr(0,11);
str_mask=str.substr(n+1,str.size());
cout<<str_mask<<endl;
IpValid(str_ip,vec);
cout<<MaskValid(str_mask);
}



6、七种情况讨论
#include <iostream>
#include <string>
#include <vector>
#include <list>
using namespace std;
bool IpValid(string str,vector<int> &vec)//添加指针,将各个数摘出来
{
for(int i=0;i<str.length();i++)
{
int j=i;
for(;j<=str.size();j++)
{
if(str[j]=='.'||j==str.size())
{
string s(str.begin()+i,str.begin()+j);//获取子串的方式
if(s.size()==0) //10..44.68避免这样情况
return false;
int num=atoi(s.c_str());//atoi将char变为int,c_str将string变为char
vec.push_back(num);
break;
}
}
i=j;
}
if(vec.size()!=4)//个数判断
return false;
for(int i=0;i<vec.size();i++)
{
if(vec[i]<0||vec[i]>255)//范围判断
return false;
}
return true;
}
void NumtoVec(int num,vector<int> &box)//逆序存放,将数字转为8位的二进制存放
{ //形参中添加vector,是想将数字从函数内传递传去
vector<int> box1;
int n;
int m=0;
while(num>=0 && m<8)
{
n=num%2;
box1.push_back(n);
num=num/2;
m++;
}
for(int i=0;i<box1.size();i++)//逆序变正
{
box.push_back(box1[box1.size()-i-1]);//255.255.255.0 --> 1111111111111111111111110000000
}
}
bool MaskValid(string str)
{
vector<int> vec;
vector<int> box;
if(IpValid(str,vec)==false) //不满足则退出
return false;
for(int i=0;i<vec.size();i++)
{
NumtoVec(vec[i],box);
}
int n=box.size(),m=-1;//1逆序查找,0正序查找,如果1的下标大于0,说明不符合
for(int i=0;i<box.size();i++)
{
if(box[i]==0)
{
n=i;
break;
}
}
for(int i=box.size()-1;i>=0;i--)
{
if(box[i]==1)
{
m=i;
break;
}
}
if(n==box.size()||m==-1)
return false;
else if(n<m)
return false;
else
return true;
}
int main()
{
//string str= "10.70.44.68~255.255.255.0";
string str;
int ip_a=0,ip_b=0,ip_c=0,ip_d=0,ip_e=0,ip_err=0,ip_pri=0;//定义初始值
while(getline(cin,str))
{
vector<int> vec;
string str_ip,str_mask;
int n=str.find('~');
str_ip=str.substr(0,n);
str_mask=str.substr(n+1,str.size());
if(IpValid(str_ip,vec)&&MaskValid(str_mask))
{
if(vec[0]>=1&&vec[0]<=126)
{
if(vec[0]==10)
ip_pri++;
ip_a++;
}
else if(vec[0]>=128&&vec[0]<=191)
{
if(vec[0]==172&&(vec[1]>=16&&vec[1]<=31))
ip_pri++;
ip_b++;
}
else if(vec[0]>=192&&vec[0]<=223)
{
if(vec[0]==192&&vec[1]==168)
ip_pri++;
ip_c++;
}
else if(vec[0]>=224&&vec[0]<=239)
{
ip_d++;
}
else if(vec[0]>=240&&vec[0]<=255)
{
ip_e++;
}
}
else
{
ip_err++;
}
}
cout<<ip_a<<" "<<ip_b<<" "<<ip_c<<" "<<ip_d<<" "<<ip_e<<" "<<ip_err<<" "<<ip_pri<<endl;
return 0;
}

7、
测试案例
测试用例: 206.76.161.30~255.0.0.0 159.70.213.68~255.0.0.0 181.131.118.0~255.255.255.0 80.164.71.44~255.255.255.255 12.208.232.42~255.255.0.0 150.24.121.174~255.0.102.0 131.221.165.68~255.0.0.0 160.126.59.101~255.0.75.0
236.239.205.137~255.255.0.0 89.124.33.74~255.0.0.159 233.174.151.221~255.255.0.0 218.140.130.246~255.255.255.255 13.13.219.143~255.0.0.0 232.95.224.67~255.255.255.255 2.108.39.131~255.0.0.0 161.217.200.192~255.0.0.0
123.170.177.162~255.0.0.0 239.64.91.24~255.0.0.0 241.199.108.210~255.255.255.0 117.0.169.232~255.255.255.255 122.49.165.60~255.255.242.255 71.148.13.251~255.0.0.32 199.22.216.173~255.254.27.0 58.24.55.101~255.132.255.0
68.128.113.136~255.0.0.0 197.234.247.46~255.255.255.0 79.22.71.93~255.255.0.0 250.217.239.76~255.0.8.0 153.96.7.235~255.255.0.0 237.173.48.19~255.0.0.0 140.48.84.23~255.255.255.0 107.222.50.243~255.0.0.0
189.224.126.176~255.255.255.0 111.9.155.102~255.0.0.0 117.4.142.205~255.255.255.255 59.0.177.100~255.255.0.0 60.70.81.248~255.255.255.255 72.85.2.100~255.255.125.0 74.15.130.23~255.0.0.0 37.51.172.97~255.255.255.149
51.58.149.175~255.0.0.0 76.106.99.1~255.255.0.0 198.102.96.87~255.255.0.0 97.170.76.38~255.0.214.0 42.115.213.173~255.255.0.0 95.115.180.128~255.255.0.0 192.240.88.125~255.0.0.47 148.36.118.39~255.0.0.0
237.211.17.109~255.255.255.255 161.230.133.200~255.0.0.0 163.139.243.139~255.0.0.0 249.174.134.36~255.255.255.0 148.64.179.63~255.0.0.0 59.156.109.132~255.0.0.0 42.50.113.7~255.0.0.0 225.95.158.160~255.0.0.0
133.17.112.129~255.0.152.0 212.183.133.49~255.255.0.0 183.12.213.169~255.255.255.255 7.144.20.194~255.255.0.0 106.46.24.252~255.255.255.255 51.181.112.115~255.0.0.0 47.243.149.186~255.255.255.0 174.11.159.234~255.0.0.0
8.83.231.207~255.0.0.0 212.211.51.229~255.0.0.0 6.13.59.212~255.255.119.0 131.151.60.159~255.0.0.0 47.21.57.12~255.0.0.0 136.242.238.159~255.0.0.0 249.200.157.157~255.255.255.0 150.2.21.239~255.0.0.0 26.100.58.90~255.226.0.0
7.167.169.193~255.255.255.0 48.49.16.45~255.132.0.0 67.244.5.142~255.0.189.0 239.170.232.59~255.0.0.0 223.138.166.166~255.0.0.103 199.65.124.179~255.255.0.0 231.121.177.81~255.255.186.193 30.247.220.230~255.255.255.0
227.72.33.192~255.255.255.255 126.189.96.104~255.255.167.255 对应输出应该为: 23 15 6 6 3 30 0
九、

这题是一种新的形式,swap_with_zero函数是已知的,只需直接调用就行,而需要自己编写sort函数,问题就是没法再dev中调试。
1、
十、
三个空汽水瓶可以换一瓶汽水。小张手上有十个空汽水瓶,她最多可以换多少瓶汽水喝?”答案是5瓶,方法如下:先用9个空瓶子换3瓶汽水,喝掉3瓶满的,喝完以后4个空瓶子,用3个再换一瓶,喝掉这瓶满的,这时候剩2个空瓶子。然后你让老板先借给你一瓶汽水,喝掉这瓶满的,喝完以后用3个空瓶子换一瓶满的还给老板。如果小张手上有n个空汽水瓶,最多可以换多少瓶汽水喝?
输入描述:
输入文件最多包含10组测试数据,每个数据占一行,仅包含一个正整数n(1<=n<=100),表示小张手上的空汽水瓶数。n=0表示输入结束,你的程序不应当处理这一行。
输出描述:
对于每组测试数据,输出一行,表示最多可以喝的汽水瓶数。如果一瓶也喝不到,输出0。
输入
3 10 81 0
输出
1 5 40

1、可以看出喝到的个数是空瓶的个数的一半取整
#include<iostream>
#include<string>
using namespace std;
int main()
{
int n;
while(cin>>n)
{
cout<<n/2<<endl;
}
return 0;
}
其实说是3个空瓶换一瓶汽水,但本质上只要有两个空瓶就可以换一瓶汽水
2、递推考虑
已知1个空瓶换0瓶汽水,2个空瓶换1个汽水。
那么3个空瓶,首先用三个空瓶换一个汽水,这时剩一个空瓶,和一个空瓶情况相同了,所以dp(3)=dp(1)+1=1;
同理,dp(4)=dp(2)+1;dp(n)=dp(n-2)+1;
递推状态转移公式出来了。
#include<iostream>
using namespace std;
int Num[100]={0};//预先定义了空间空间复杂度高
int main()
{
int n;
while(cin>>n)
{
Num[1]=0;
Num[2]=1;
for(int i=3;i<=n;i++)
{
Num[i]=Num[i-2]+1;
}
cout<<Num[n]<<endl;
}
return 0;
}
3、降低空间复杂度
#include<iostream>
using namespace std;
int main()
{
int n;
while(cin>>n)
{
int l1=0,l2=1,q;
for(int i=3;i<=n;i++)
{
if(i%2==0)
l2++;
else
l1++;
}
if(n%2==0)
cout<<l2<<endl;
else
cout<<l1<<endl;
}
return 0;
}
只保留了两个数来存储变量。节省空间。
浙公网安备 33010602011771号