题解 | 判断两个IP是否属于同一子网
判断两个IP是否属于同一子网
https://www.nowcoder.com/practice/34a597ee15eb4fa2b956f4c595f03218
#include <bitset>
#include <iostream>
#include <sstream>
#include <string>
#include <vector>
using namespace std;
#define SAMPLE
string toBitString(int num)
{
return bitset<8>(num).to_string();
}
#ifndef SAMPLE
bool isValidMask(vector<int>& maskArr)
{
bool switchedZero {false};
for (const auto& num: maskArr)
{
for (const auto& ch: toBitString(num))
{
if (ch == '0') switchedZero = true;
else if (switchedZero && (ch == '1')) return false;
}
}
return true;
}
#endif
#ifdef SAMPLE
bool isValidMask(vector<int>& maskArr)
{
bool switchedZero {false};
for (const auto& num: maskArr)
{
if (switchedZero)
{
if (num == 0) continue;
return false;
}
if (!switchedZero && (num == 255)) continue;
// now 0 < num < 255
switchedZero = true;
/* solution 1
unsigned int n{static_cast<unsigned>(num)}; // could not change num, use n instead, use unsigned in case of overflowing (using move left)
while (n != 0 && (n & 0b1000'0000) != 0) { // find first 0
n <<= 1;
}
// 剩余的位必须全 0
if ((n & 0b1111'1111) != 0) {
return false;
}
*/
/* solution 2 */ // no possible overflow
unsigned int mask = 0b1000'0000;
while (mask != 0 && (num & mask) != 0) { // find first 0 of num
mask >>= 1;
}
// if num = 1110'0000, after iteration, mask is 0001'0000.
// 剩余的位必须全 0
if ((num & (mask -1 )) != 0) { // mask - 1 = 0000'1111
return false;
}
}
return true;
}
#endif
bool isValidIp(vector<int>& ipArr, const string& ip)
{
string num{};
istringstream iss(ip);
while (getline(iss, num, '.'))
{
int n{stoi(num)};
if ((n <= 255) && (n >=0))
ipArr.push_back(n);
else
{
return false;
}
}
if (ipArr.size() != 4) return false;
return true;
}
int main() {
string mask{};
string ip1{};
string ip2{};
while (cin >> mask >> ip1 >> ip2)
{
vector<int> ipArr1{};
vector<int> ipArr2{};
vector<int> maskArr{};
bool isValid(true);
isValid = isValidIp(maskArr, mask) &&
isValidMask(maskArr) &&
isValidIp(ipArr1, ip1) &&
isValidIp(ipArr2, ip2);
if (!isValid)
{
cout << 1 << "\n";
continue;
}
bool isSameSubNet{true};
for (int i{0}; i < 4; ++i)
{
if ((maskArr[i] & ip1[i]) == (maskArr[i] & ip2[i]))
continue;
else
{
isSameSubNet = false;
break;
}
}
if (isSameSubNet) cout << 0 << "\n";
else cout << 2 << "\n";
}
}
// 64 位输出请用 printf("%lld")
使用3种方法检查mask是否合法。
查看17道真题和解析