timezone_name_from_abbr() 函数根据时区缩写返回时区名称。这个函数可以根据时区缩写、偏移量(以秒为单位)和夏令时标志来查找匹配的时区。
注意:由于一个时区缩写可能对应多个时区(如 "CST" 可以表示中国标准时间或美国中部标准时间),因此可能需要结合偏移量和夏令时标志来确定具体的时区。
timezone_name_from_abbr(string $abbr [, int $utcOffset = -1 [, int $isDST = -1]]) : string|false
| 参数 | 默认值 | 描述 |
|---|---|---|
| abbr | 无 |
必需。 时区缩写。 |
| utcOffset | -1 |
可选。 以秒为单位的 UTC 偏移量。例如,对于 UTC+8,偏移量为 28800(8 * 3600)。 默认值 -1 表示不限制偏移量。 |
| isDST | -1 |
可选。 夏令时标志。 1 表示夏令时,0 表示非夏令时,-1 表示不限制。 |
成功时返回时区名称(字符串),失败时返回 false。
<?php
// 仅使用时区缩写查找
echo "EST: " . timezone_name_from_abbr("EST") . "<br>";
echo "PST: " . timezone_name_from_abbr("PST") . "<br>";
echo "GMT: " . timezone_name_from_abbr("GMT") . "<br>";
echo "CST: " . timezone_name_from_abbr("CST") . "<br>"; // 注意:CST 有多个匹配
echo "JST: " . timezone_name_from_abbr("JST") . "<br>";
echo "AEST: " . timezone_name_from_abbr("AEST") . "<br>";
// 输出类似:
// EST: America/New_York
// PST: America/Los_Angeles
// GMT: Europe/London
// CST: America/Chicago
// JST: Asia/Tokyo
// AEST: Australia/Sydney
?>
<?php
// 结合偏移量查找,解决缩写歧义
echo "CST (无偏移量): " . timezone_name_from_abbr("CST") . "<br>";
echo "CST (偏移量 -21600): " . timezone_name_from_abbr("CST", -21600) . "<br>"; // UTC-6
echo "CST (偏移量 28800): " . timezone_name_from_abbr("CST", 28800) . "<br>"; // UTC+8
// 测试不同偏移量
echo "<br>测试不同偏移量的 EST:<br>";
echo "EST (-18000): " . timezone_name_from_abbr("EST", -18000) . "<br>"; // UTC-5
echo "EST (-14400): " . timezone_name_from_abbr("EST", -14400) . "<br>"; // UTC-4 (EDT)
// 测试无效偏移量
$result = timezone_name_from_abbr("EST", 99999);
echo "EST (无效偏移量 99999): " . ($result === false ? 'false' : $result) . "<br>";
// 输出类似:
// CST (无偏移量): America/Chicago
// CST (偏移量 -21600): America/Chicago
// CST (偏移量 28800): Asia/Shanghai
//
// 测试不同偏移量的 EST:
// EST (-18000): America/New_York
// EST (-14400): false
// EST (无效偏移量 99999): false
?>
<?php
// 结合夏令时标志查找
echo "<h4>EST 的不同组合:</h4>";
echo "EST (无限制): " . timezone_name_from_abbr("EST") . "<br>";
echo "EST (非夏令时): " . timezone_name_from_abbr("EST", -1, 0) . "<br>";
echo "EST (夏令时): " . timezone_name_from_abbr("EST", -1, 1) . "<br>";
echo "<h4>EDT 的不同组合:</h4>";
echo "EDT (无限制): " . timezone_name_from_abbr("EDT") . "<br>";
echo "EDT (非夏令时): " . timezone_name_from_abbr("EDT", -1, 0) . "<br>";
echo "EDT (夏令时): " . timezone_name_from_abbr("EDT", -1, 1) . "<br>";
echo "<h4>PDT 的不同组合:</h4>";
echo "PDT (无限制): " . timezone_name_from_abbr("PDT") . "<br>";
echo "PDT (偏移量 -25200, 夏令时): " . timezone_name_from_abbr("PDT", -25200, 1) . "<br>"; // UTC-7
// 输出类似:
// EST 的不同组合:
// EST (无限制): America/New_York
// EST (非夏令时): America/New_York
// EST (夏令时): false
//
// EDT 的不同组合:
// EDT (无限制): America/New_York
// EDT (非夏令时): false
// EDT (夏令时): America/New_York
//
// PDT 的不同组合:
// PDT (无限制): America/Los_Angeles
// PDT (偏移量 -25200, 夏令时): America/Los_Angeles
?>
<?php
// 处理有歧义的时区缩写
function getPossibleTimezonesFromAbbr($abbr, $offset = -1, $isDST = -1) {
$abbreviations = timezone_abbreviations_list();
$abbr = strtolower($abbr);
$results = [];
if (isset($abbreviations[$abbr])) {
foreach ($abbreviations[$abbr] as $info) {
// 检查偏移量
if ($offset != -1 && $info['offset'] != $offset) {
continue;
}
// 检查夏令时
if ($isDST != -1 && $info['dst'] != ($isDST == 1)) {
continue;
}
$results[] = [
'timezone_id' => $info['timezone_id'],
'offset' => $info['offset'],
'dst' => $info['dst']
];
}
}
return $results;
}
// 测试 CST 的所有可能时区
echo "<h4>CST 的所有可能时区:</h4>";
$cst_timezones = getPossibleTimezonesFromAbbr("CST");
foreach ($cst_timezones as $tz) {
$hours = $tz['offset'] / 3600;
echo "时区: " . $tz['timezone_id'] .
", 偏移量: " . $tz['offset'] . " 秒 (UTC" . ($hours >= 0 ? '+' : '') . $hours . ")" .
", 夏令时: " . ($tz['dst'] ? '是' : '否') . "<br>";
}
echo "<h4>CST (偏移量 28800) 的时区:</h4>";
$cst_utc8 = getPossibleTimezonesFromAbbr("CST", 28800);
if (empty($cst_utc8)) {
echo "无匹配时区<br>";
} else {
foreach ($cst_utc8 as $tz) {
echo "时区: " . $tz['timezone_id'] . "<br>";
}
}
// 输出类似:
// CST 的所有可能时区:
// 时区: America/Chicago, 偏移量: -21600 秒 (UTC-6), 夏令时: 否
// 时区: America/Havana, 偏移量: -18000 秒 (UTC-5), 夏令时: 否
// 时区: Asia/Shanghai, 偏移量: 28800 秒 (UTC+8), 夏令时: 否
// 时区: Asia/Taipei, 偏移量: 28800 秒 (UTC+8), 夏令时: 否
// ... 更多
//
// CST (偏移量 28800) 的时区:
// 时区: Asia/Shanghai
// 时区: Asia/Taipei
?>
<?php
// 从偏移量获取时区名称(不使用缩写)
function getTimezoneFromOffset($offset_hours, $isDST = -1) {
$offset_seconds = $offset_hours * 3600;
// 尝试常见的缩写
$common_abbrs = [
'EST' => -5, 'EDT' => -4,
'CST' => -6, 'CDT' => -5,
'MST' => -7, 'MDT' => -6,
'PST' => -8, 'PDT' => -7,
'GMT' => 0, 'BST' => 1,
'CET' => 1, 'CEST' => 2,
'IST' => 5.5, 'JST' => 9,
'CST' => 8, 'AEST' => 10, 'AEDT' => 11
];
foreach ($common_abbrs as $abbr => $hours) {
if ($hours == $offset_hours) {
$result = timezone_name_from_abbr($abbr, $offset_seconds, $isDST);
if ($result !== false) {
return $result;
}
}
}
// 如果没有匹配的缩写,尝试使用空字符串
$result = timezone_name_from_abbr("", $offset_seconds, $isDST);
if ($result !== false) {
return $result;
}
return false;
}
// 测试
echo "<h4>从偏移量获取时区:</h4>";
$offsets = [-8, -5, 0, 8, 9.5, 12];
foreach ($offsets as $offset) {
$timezone = getTimezoneFromOffset($offset);
echo "UTC" . ($offset >= 0 ? '+' : '') . $offset . ": " .
($timezone ? $timezone : '未找到') . "<br>";
}
// 输出类似:
// 从偏移量获取时区:
// UTC-8: America/Los_Angeles
// UTC-5: America/New_York
// UTC+0: Europe/London
// UTC+8: Asia/Shanghai
// UTC+9.5: Australia/Adelaide
// UTC+12: Pacific/Auckland
?>
<?php
// 安全地处理用户输入的时区缩写
function sanitizeTimezoneFromUserInput($input, $offset_hours = null) {
// 清理输入
$abbr = strtoupper(trim($input));
if (empty($abbr)) {
return ['success' => false, 'message' => '时区缩写不能为空'];
}
// 如果提供了偏移量
$offset_seconds = ($offset_hours !== null) ? $offset_hours * 3600 : -1;
// 尝试获取时区名称
$timezone_name = timezone_name_from_abbr($abbr, $offset_seconds);
if ($timezone_name === false) {
// 尝试不区分大小写
$timezone_name = timezone_name_from_abbr(strtolower($abbr), $offset_seconds);
}
if ($timezone_name !== false) {
return [
'success' => true,
'timezone' => $timezone_name,
'abbr' => $abbr,
'offset_hours' => $offset_hours
];
} else {
return [
'success' => false,
'message' => "无法找到时区缩写 '{$abbr}'" .
($offset_hours !== null ? " (偏移量 UTC" .
($offset_hours >= 0 ? '+' : '') . $offset_hours . ")" : "")
];
}
}
// 测试用户输入
$test_inputs = [
['est', null],
['pst', -8],
['cst', 8],
['jst', null],
['invalid', null],
['', null]
];
foreach ($test_inputs as $input) {
list($abbr, $offset) = $input;
$result = sanitizeTimezoneFromUserInput($abbr, $offset);
echo "<strong>输入:</strong> '{$abbr}'" .
($offset !== null ? " (偏移量 UTC" . ($offset >= 0 ? '+' : '') . $offset . ")" : "") .
"<br>";
if ($result['success']) {
echo "<span style='color: green;'>✓ 找到时区: " . $result['timezone'] . "</span>";
} else {
echo "<span style='color: red;'>✗ " . $result['message'] . "</span>";
}
echo "<br><br>";
}
// 输出类似:
// 输入: 'est' (偏移量 UTC-5)
// ✓ 找到时区: America/New_York
//
// 输入: 'pst' (偏移量 UTC-8)
// ✓ 找到时区: America/Los_Angeles
//
// 输入: 'cst' (偏移量 UTC+8)
// ✓ 找到时区: Asia/Shanghai
//
// 输入: 'jst'
// ✓ 找到时区: Asia/Tokyo
//
// 输入: 'invalid'
// ✗ 无法找到时区缩写 'INVALID'
//
// 输入: ''
// ✗ 时区缩写不能为空
?>
<?php
// 与其他时区函数配合使用
function getDetailedTimezoneInfo($abbr, $offset_hours = null, $isDST = -1) {
$offset_seconds = ($offset_hours !== null) ? $offset_hours * 3600 : -1;
// 获取时区名称
$timezone_name = timezone_name_from_abbr($abbr, $offset_seconds, $isDST);
if ($timezone_name === false) {
return ['error' => '未找到匹配的时区'];
}
try {
// 创建 DateTimeZone 对象
$timezone = new DateTimeZone($timezone_name);
// 获取位置信息
$location = timezone_location_get($timezone);
// 获取当前偏移量
$now = new DateTime('now', $timezone);
$current_offset = $timezone->getOffset($now);
// 获取时区缩写列表
$abbreviations = timezone_abbreviations_list();
$abbr_lower = strtolower($abbr);
$abbr_info = isset($abbreviations[$abbr_lower]) ? $abbreviations[$abbr_lower] : [];
return [
'timezone_name' => $timezone_name,
'current_offset' => $current_offset,
'current_offset_hours' => $current_offset / 3600,
'location' => $location !== false ? $location : '无位置信息',
'matching_abbr_info' => $abbr_info
];
} catch (Exception $e) {
return ['error' => $e->getMessage()];
}
}
// 获取 EST 的详细信息
echo "<h4>EST 的详细信息:</h4>";
$est_info = getDetailedTimezoneInfo('EST');
if (isset($est_info['error'])) {
echo "错误: " . $est_info['error'];
} else {
echo "<pre>";
print_r($est_info);
echo "</pre>";
}
// 输出类似:
// EST 的详细信息:
// Array
// (
// [timezone_name] => America/New_York
// [current_offset] => -14400
// [current_offset_hours] => -4
// [location] => Array
// (
// [country_code] => US
// [latitude] => 40.7142
// [longitude] => -74.0064
// [comments] =>
// )
// [matching_abbr_info] => Array
// (
// [0] => Array
// (
// [dst] =>
// [offset] => -18000
// [timezone_id] => America/New_York
// )
// ... 更多
// )
// )
?>
| 缩写 | 含义 | 常见时区 | 标准时间偏移 (UTC) | 夏令时偏移 (UTC) |
|---|---|---|---|---|
| EST | Eastern Standard Time | America/New_York | -5 | -4 (EDT) |
| CST | Central Standard Time | America/Chicago | -6 | -5 (CDT) |
| MST | Mountain Standard Time | America/Denver | -7 | -6 (MDT) |
| PST | Pacific Standard Time | America/Los_Angeles | -8 | -7 (PDT) |
| GMT | Greenwich Mean Time | Europe/London | 0 | +1 (BST) |
| CET | Central European Time | Europe/Paris | +1 | +2 (CEST) |
| EET | Eastern European Time | Europe/Helsinki | +2 | +3 (EEST) |
| CST | China Standard Time | Asia/Shanghai | +8 | +8 (无夏令时) |
| JST | Japan Standard Time | Asia/Tokyo | +9 | +9 (无夏令时) |
| AEST | Australian Eastern Standard Time | Australia/Sydney | +10 | +11 (AEDT) |
| IST | Indian Standard Time | Asia/Kolkata | +5.5 | +5.5 (无夏令时) |
DateTimeZone 类进行更复杂的时区操作