题解 | #识别有效的IP地址和掩码并进行分类统计#
识别有效的IP地址和掩码并进行分类统计
https://www.nowcoder.com/practice/de538edd6f7e4bc3a5689723a7435682
#include <iostream>
#include <string>
#include <vector>
#include <bitset>
using namespace std;
int main() {
string str,str1,str2,str3,str4;
int pos;
vector<int> num1,num2;
int cout_a=0,cout_b=0,cout_c=0,cout_d=0,cout_e=0,cout_err=0,cout_err_now=0,cout_private=0;
while (getline(cin,str)) { // 注意 while 处理多个 case
pos=str.find('~');
str1.append(str,0,pos);
str2.append(str,pos+1,str.size()-1);
for(int i=0;i<str1.size();i++){
if(str1[i]!='.'){
str3+=str1[i];
}
else if(str1[i]=='.'&&str3!=""){ //处理19..0.
num1.push_back(stoi(str3));
str3="";
}
}
if(str3!="") num1.push_back(stoi(str3));//添加ip地址最后一位
str1="";
str3="";
for(int j=0;j<str2.size();j++){
if(str2[j]!='.'){
str4+=str2[j];
}
else if(str2[j]=='.'&&str4!=""){ //处理19..0.
num2.push_back(stoi(str4));
str4="";
}
}
if(str4!="") num2.push_back(stoi(str4));//添加ip地址最后一位
str2="";
str4="";
//判断子网掩码
if(num2.size()==4){
bitset<8> bits1(num2[0]);
bitset<8> bits2(num2[1]);
bitset<8> bits3(num2[2]);
bitset<8> bits4(num2[3]);
string str_1=bits1.to_string();
string str_2=bits2.to_string();
string str_3=bits3.to_string();
string str_4=bits4.to_string();
string str_5=str_1+str_2+str_3+str_4;
int pos=str_5.find("01");
if(pos!=-1 || \
(num2[0]==255&&num2[1]==255&&num2[2]==255&&num2[3]==255) || \
(num2[0]==0 &&num2[1]==0 &&num2[2]==0 &&num2[3]==0) ){//如果找到01
cout_err_now=1;//cout_err_now代表本次子网掩码是否错误
}
}
//判断a~e 有效ip
if(num1.size()==4 && cout_err_now==0 && \
num1[0]>=1&&num1[0]<=126 && \
num1[1]>=0&&num1[1]<=255 && \
num1[2]>=0&&num1[2]<=255 && \
num1[3]>=0&&num1[3]<=255 ){
cout_a++;
}
else if(num1.size()==4 && cout_err_now==0 && \
num1[0]>=128&&num1[0]<=191 && \
num1[1]>=0&&num1[1]<=255 && \
num1[2]>=0&&num1[2]<=255 && \
num1[3]>=0&&num1[3]<=255 ){
cout_b++;
}
else if(num1.size()==4 && cout_err_now==0 && \
num1[0]>=192&&num1[0]<=223 && \
num1[1]>=0&&num1[1]<=255 && \
num1[2]>=0&&num1[2]<=255 && \
num1[3]>=0&&num1[3]<=255 ){
cout_c++;
}
else if(num1.size()==4 && cout_err_now==0 && \
num1[0]>=224&&num1[0]<=239 && \
num1[1]>=0&&num1[1]<=255 && \
num1[2]>=0&&num1[2]<=255 && \
num1[3]>=0&&num1[3]<=255 ){
cout_d++;
}
else if(num1.size()==4 && cout_err_now==0 && \
num1[0]>=240&&num1[0]<=255 && \
num1[1]>=0&&num1[1]<=255 && \
num1[2]>=0&&num1[2]<=255 && \
num1[3]>=0&&num1[3]<=255 ){
cout_e++;
}
else if(num1[0]==0 || num1[0]==127 ){//注意这里一定不能加num1.size()==4 && cout_err_now==0 因为这个不在计数范围内
}
else{
cout_err++;
}
//判断私有ip
if(num1.size()==4 && cout_err_now==0 && \
(num1[0]==10 && \
num1[1]>=0 && num1[1]<=255 && \
num1[2]>=0 && num1[2]<=255 && \
num1[3]>=0 && num1[3]<=255)|| \
(num1[0]==172 && \
num1[1]>=16 && num1[1]<=31 && \
num1[2]>=0 && num1[2]<=255 && \
num1[3]>=0 && num1[3]<=255)|| \
(num1[0]==192 && \
num1[1]==168 && \
num1[2]>=0 && num1[2]<=255 && \
num1[3]>=0 && num1[3]<=255) ){
cout_private++;
}
num1={};
num2={};
cout_err_now=0;//本次的判断完,cout_err_now清零
}
cout<< cout_a <<" "<< cout_b<<" "<<cout_c<<" "<<cout_d<<" "<<cout_e<<" "<<cout_err<<" "<<cout_private<<endl;
}
// 64 位输出请用 printf("%lld")
解题思路:
关于输入输出:输入为一行字符串,可以直接用getline(cin,str)
关于判断ip类型:先把字符串的ip和子网掩码分开,利用find('~')即可。然后把ip的每个.隔开的字符串变成int,利用stoi(str),用vector保存每部分的数,然后比较其范围。
关于判断子网掩码类型:同理把每个.隔开的字符串变成int,然后根据子网掩码的特点,前面是连续1后面连续0,需要把int转化成二进制,可以利用bitset<8> bits(n),然后把二进制转成字符串,利用bits.to_string(),最后搜索里面有没有“01”出现。
阿里巴巴灵犀互娱公司福利 668人发布