屎山终于A了这道题了!!!!!!

用三个函数judgeIP 、 judgeprivate 、 judgemask 来分别判断是否合法

我感觉主要的坑点就是,当ip地址是0或者127的时候,即便它的mask是不合法的,那么也不应该算入到不合法的计数里面

#include <iostream>
#include <string>
#include <sstream>
using namespace std;

int ans[7];

int judgeIP(string ip) {
    stringstream ss(ip);
    int count = 0;
    int ip_temp[4] ;
    string temp;
    while (getline(ss, temp, '.')) {
        if (temp.size() == 0) return -1; // ip少了, 不合法直接返回0
        ip_temp[count] = stoi(temp);
        count++;
    }
    if (count != 4) return -1;
    for (int i = 0; i < 4; i++) { // 判断ip每一位的合法性
        if (ip_temp[i] <= 255 && ip_temp[i] >= 0) continue;
        return -1;
    }

    if(ip_temp[0] >= 1 && ip_temp[0] <= 126) return 1;
    else if(ip_temp[0] >= 128 && ip_temp[0] <= 191) return 2;
    else if(ip_temp[0] >= 192 && ip_temp[0] <= 223) return 3;
    else if(ip_temp[0] >= 224 && ip_temp[0] <= 239) return 4;
    else if(ip_temp[0] >= 240 && ip_temp[0] <= 255) return 5;

    return 0;
}

int judgePrivate(string ip) {
    stringstream ss(ip);
    int count = 0;
    int ip_temp[4] ;
    string temp;
    while (getline(ss, temp, '.')) {
        if (temp.size() == 0) return -1; // ip少了, 不合法直接返回0
        ip_temp[count] = stoi(temp);
        count++;
    }
    if (count != 4) return -1;
    for (int i = 0; i < 4; i++) { // 判断ip每一位的合法性
        if (ip_temp[i] <= 255 && ip_temp[i] >= 0) continue;
        return -1;
    }


    if (ip_temp[0] == 10) return 1;
    else if (ip_temp[0] == 172 && ip_temp[1] >= 16 && ip_temp[2] <= 31) return 2;
    else if (ip_temp[0] == 192 && ip_temp[1] == 168 ) return 3;
    return 0;
}

int judgeMask(string mask) {
    stringstream ss(mask);
    int count = 0; //从1到0可以,从0到1不可以
    string mask_all_binary = "";
    string mask_part_string = "";
    while (getline(ss, mask_part_string, '.')) {
        if (mask_part_string.size() == 0) return -1; // 子网掩码少了, 不合法直接返回0
        int mask_part_int = stoi(mask_part_string);
        count++;
        string mask_part_binary = "";
        while(mask_part_int){
            mask_part_binary = to_string(mask_part_int%2) + mask_part_binary;
            mask_part_int /= 2;
        }
        while(mask_part_binary.size() < 8) {
            mask_part_binary = "0" + mask_part_binary;
        }
        mask_all_binary = mask_all_binary + mask_part_binary;
    }
    if(mask_all_binary == "00000000000000000000000000000000" || mask_all_binary == "11111111111111111111111111111111") return -1;

    char flag = '1'; // 前面已经遍历过的数字
    for(int i = 0; i < 32; i++){
        if(mask_all_binary[i] == '1' && flag == '0') return -1;
        flag = mask_all_binary[i] ;
    }
    return 1;
}

void count(string ip, string mask) {
    int ip_public = judgeIP(ip);
    int ip_private = judgePrivate(ip);
    int ip_mask = judgeMask(mask);

    if(ip_public == -1 || (ip_mask == -1 && ip_public != 0)) {
        ans[5]++;
        // cout << ip << ' ' << mask << ' ' << endl;
        return;
    }

    if(ip_public == 1) ans[0]++;
    else if(ip_public == 2) ans[1]++;
    else if(ip_public == 3) ans[2]++;
    else if(ip_public == 4) ans[3]++;
    else if(ip_public == 5) ans[4]++;

    if(ip_private == 1 || ip_private == 2 || ip_private == 3 ) ans[6]++;
    return;
}



int main() {
    string str;
    while (getline(cin, str)) {
        string ip = str.substr(0, str.find('~'));
        string mask = str.substr(str.find('~') + 1);
        count(ip, mask);
    }

    for(int i = 0; i < 7; i++){
        cout << ans[i] << ' ';
    }
}
// 64 位输出请用 printf("%lld")