給定 CIDR 表示法(如 `192.168.1.5/24`),核心步驟:
// 掩碼位數轉二進制字符串
function mask2bin($n) {
$n = intval($n);
if ($n < 0 || $n > 32) die('error submask');
return str_repeat("1", $n) . str_repeat("0", 32 - $n);
}
// 二進制取反
function revBin($s) {
return str_replace(['0','1','2'], ['2','0','1'], $s);
}
// 計算網段起始 IP(單字節)
function startIp($str, $bSub) {
$bIp = str_pad(decbin($str), 8, "0", STR_PAD_LEFT);
return bindec($bIp & $bSub);
}
// 計算網段結束 IP(單字節)
function endIp($str, $bSub) {
$bIp = str_pad(decbin($str), 8, "0", STR_PAD_LEFT);
return bindec($bIp | revBin($bSub));
}
$ip = ['192', '168', '1', '5'];
$mask = '24';
$bSub = mask2bin($mask);
// 掩碼分段
$maskArr = [
substr($bSub, 0, 8),
substr($bSub, 8, 8),
substr($bSub, 16, 8),
substr($bSub, 24, 8)
];
// 輸出結果
echo "掩碼: " . implode('.', array_map('bindec', $maskArr)) . "\n";
echo "網絡地址: ";
for ($i=0;$i<4;$i++) echo startIp($ip[$i], $maskArr[$i]) . ($i!=3?'.':'');
echo "\n首個可用: ";
for ($i=0;$i<3;$i++) echo startIp($ip[$i], $maskArr[$i]) . '.';
echo (startIp($ip[3], $maskArr[3]) + 1) . "\n";
echo "最後可用: ";
for ($i=0;$i<3;$i++) echo endIp($ip[$i], $maskArr[$i]) . '.';
echo (endIp($ip[3], $maskArr[3]) - 1) . "\n";
echo "廣播地址: " . implode('.', array_map(fn($i)=>endIp($ip[$i], $maskArr[$i]), range(0,3)));
PHP 7.0+ 可使用 `ip2long`/`long2ip` 簡化運算,或直接引入 `myclabs/php-ip` 等成熟庫處理 IPv4/IPv6 統一計算。
掌握位運算與 CIDR 核心邏輯,即可靈活實現 IP 範圍計算、子網劃分、防火牆規則生成等網絡編程任務。