[FIX] 修正台灣地址解析經緯度失敗問題

1. 新增 cleanFloorInfo 方法,過濾地址末尾的樓層、室、地下室等非門牌雜訊,防範 Nominatim 解析失敗。
2. 重構 parseTaiwanAddress 的路名拆分正則表達式,導入層級感知台灣地址結構,避免含有「巷、弄」的地址被提前截斷。
This commit is contained in:
sky121113 2026-05-22 09:51:05 +08:00
parent b6e5b825a5
commit 4dad775568

View File

@ -25,6 +25,9 @@ class GeocodingController extends Controller
$address = $request->input('address');
// 1. 清洗台灣地址中的樓層、室、地下室與括號備註,避免干擾地理編碼解析
$address = $this->cleanFloorInfo($address);
// 策略 1結構化搜尋台灣地址精確度最高
$parsed = $this->parseTaiwanAddress($address);
@ -114,8 +117,8 @@ class GeocodingController extends Controller
$streetPart = $address;
}
// 拆分路名與門牌號碼
preg_match('/^(.+?(?:路|街|大道|巷|弄)(?:[一二三四五六七八九十]+段)?)\s*(.*)/u', $streetPart, $roadMatch);
// 拆分路名與門牌號碼(層級感知台灣地址結構,完整保留巷弄)
preg_match('/^(.+?(?:路|街|大道)(?:[一二三四五六七八九十]+段)?(?:[0-9一二三四五六七八九十百]+巷)?(?:[0-9一二三四五六七八九十百]+弄)?)\s*(.*)/u', $streetPart, $roadMatch);
$street = '';
$houseNumber = '';
@ -134,4 +137,21 @@ class GeocodingController extends Controller
'street' => $fullStreet,
];
}
/**
* 清洗台灣地址中的樓層、室、地下室與括號備註,避免干擾 OpenStreetMap 解析
*/
private function cleanFloorInfo(string $address): string
{
// 1. 移除常見的樓層與地下室資訊,以及其後方的所有贅字:例如 "2樓", "12樓之3", "89F", "B1", "地下1樓" 等
$address = preg_replace('/(?:地下一?|地下)?(?:[0-9一二三四五六七八九十百]+樓|[0-9a-zA-Z]+[fF]|[bB][0-9]+)(?:之[0-9一二三四五六七八九十百]+)?.*/u', '', $address);
// 2. 移除 "x室", "x房", "x戶" 等室內資訊
$address = preg_replace('/(?:[0-9a-zA-Z一二三四五六七八九十百]+(?:室|房|戶)).*/u', '', $address);
// 3. 移除常見 the 括號備註,例如 "(五樓)", "(A棟)", "(總統府)"
$address = preg_replace('/[\(][^\)]+[\)]/u', '', $address);
return trim($address);
}
}