JavaScript 日期處理與格式化
tags: JavaScript
日期格式化 (Date物件)
Safari
Safari 接受的
new Date
格式與後端常見格式不同:
- 後端常見格式:
xxxx-xx-xx xx:xx:xx.00000
- Safari 接受格式:
xxxx/xx/xxTxx:xx:xx
方法一:針對 Safari 截斷字串
javascript
if (/Safari/.test(navigator.userAgent) && !/Chrome/.test(navigator.userAgent)) {
return times.substr(0, 19);
}
方法二:統一替換空格為 "T"
javascript
const date = new Date(typeof time === 'string' ? time.replace(/ /g, "T") : time);
單一日期格式化函數
typescript
const padZero = (num: number) => num < 10 ? `0${num}` : `${num}`;
const formatSingleDate = (date: Date, formatType: 1 | 2 = 1): string => {
const year = date.getFullYear();
const month = padZero(date.getMonth() + 1);
const day = padZero(date.getDate());
const hours = padZero(date.getHours());
const minutes = padZero(date.getMinutes());
if (formatType === 1) return `${year}-${month}-${day}`; // YYYY-MM-DD
if (formatType === 2) return `${year}-${month}-${day} ${hours}:${minutes}`; // YYYY-MM-DD hh:mm
return '';
};
YYYY-MM-DD
times 為 number 的情況有可能會是時間戳
typescript
export function getFormatYMD(times: string || number) {
let date = new Date(times)
let dateYear = date.getFullYear();
let dateMonth = date.getMonth() < 9 ? "0" + (date.getMonth() + 1) : (date.getMonth() + 1);
let dateDate = date.getDate() < 10 ? "0" + date.getDate() : date.getDate();
let todayFormat = `${dateYear}-${dateMonth}-${dateDate}`
return todayFormat
}
YYYY-MM-DD hh:mm
typescript
export function getFormatYMDHM(times: string) {
let date = new Date(times);
let dateYear = date.getFullYear();
let dateMonth = date.getMonth() < 9 ? "0" + (date.getMonth() + 1) : (date.getMonth() + 1);
let dateDate = date.getDate() < 10 ? "0" + date.getDate() : date.getDate();
let dateHour = date.getHours() < 10 ? '0' + date.getHours() : date.getHours();
let dateMin = date.getMinutes() < 10 ? '0' + date.getMinutes() : date.getMinutes();
return `${dateYear}-${dateMonth}-${dateDate} ${dateHour}:${dateMin}`;
}
日期範圍格式化
日期範圍預設值
typescript
const getDefaultDateRange = (): [Date, Date] => {
const endDate = new Date(); // 當前時間
endDate.setHours(23, 0, 0, 0); // 設為 23:00
const startDate = new Date(endDate);
startDate.setDate(endDate.getDate() - 30); // 往前推 30 天
startDate.setHours(0, 0, 0, 0); // 設為 00:00
return [startDate, endDate];
};
格式化日期範圍
typescript
const formatDateRange = (dates: [Date, Date] | Date, formatType: 1 | 2 | 3): string => {
const padZero = (num: number) => num < 10 ? `0${num}` : `${num}`;
const formatSingle = (date: Date): string => {
const year = date.getFullYear();
const month = padZero(date.getMonth() + 1);
const day = padZero(date.getDate());
const hours = padZero(date.getHours());
const minutes = padZero(date.getMinutes());
if (formatType === 1) return `${year}-${month}-${day}`;
if (formatType === 2) return `${year}-${month}-${day} ${hours}:${minutes}`;
if (formatType === 3) return `${year}-${month}-${day}`;
return '';
};
if (Array.isArray(dates)) {
const startDate = formatSingle(dates[0]);
const endDate = formatSingle(dates[1]);
if (formatType === 1) return `${startDate}~${endDate}`; // YYYY-MM-DD~YYYY-MM-DD
if (formatType === 2) return `${startDate}~${endDate}`; // YYYY-MM-DD hh:mm~YYYY-MM-DD hh:mm
if (formatType === 3) return endDate; // YYYY-MM-DD (僅結束日期)
} else {
return formatSingle(dates); // 單一日期
}
return '';
};
使用範例
javascript
const dateTime = [new Date(2000, 10, 10, 10, 10), new Date(2000, 10, 11, 10, 10)];
console.log(formatDateRange(dateTime, 1)); // "2000-11-10~2000-11-11"
console.log(formatDateRange(new Date(), 3)); // "2025-03-09"
特規
後端想要拿到的格式:
typescript
{
time_start_day: string
time_start_hour: string
time_end_day: string
time_end_hour: string
}
typescript
const getDateRangeObject = (dates: [Date, Date]): {
time_start_day: string;
time_start_hour: string;
time_end_day: string;
time_end_hour: string;
} => {
const padZero = (num: number) => num < 10 ? `0${num}` : `${num}`;
const start = dates[0];
const end = dates[1];
return {
time_start_day: `${start.getFullYear()}-${padZero(start.getMonth() + 1)}-${padZero(start.getDate())}`,
time_start_hour: `${padZero(start.getHours())}:${padZero(start.getMinutes())}`,
time_end_day: `${end.getFullYear()}-${padZero(end.getMonth() + 1)}-${padZero(end.getDate())}`,
time_end_hour: `${padZero(end.getHours())}:${padZero(end.getMinutes())}`
};
};
字串格式轉換
xxxx-xx-xx → xxxx年xx月xx日
_ 是整個符合的字串,也就是 "1921-05-23"。 year 是第一個捕獲組 (\d{4}) 的匹配結果,即 "1921"。 month 是第二個捕獲組 (\d{2}) 的匹配結果,即 "05"。 day 是第三個捕獲組 (\d{2}) 的匹配結果,即 "23"。
javascript
const dateString = "1921-05-23";
const formattedDate = dateString.replace(
/(\d{4})-(\d{2})-(\d{2})/,
(_, year, month, day) => `${year}年${month}月${day}日`
);
// 結果: "1921年05月23日"
日期切換
上下月
javascript
export function getFormatTransYM(times: string, type: 'prev' | 'next'): string {
let date = new Date(times);
let dateYear = date.getFullYear();
let dateMonth: string;
if (type === 'prev') {
let tempMonth = date.getMonth() < 9 ? "0" + date.getMonth() : date.getMonth();
if (tempMonth === "00") {
dateYear -= 1;
dateMonth = "12";
} else {
dateMonth = tempMonth;
}
} else {
let tempMonth = date.getMonth() + 2 < 10 ? "0" + (date.getMonth() + 2) : (date.getMonth() + 2);
if (tempMonth === "13") {
dateYear += 1;
dateMonth = "01";
} else {
dateMonth = tempMonth;
}
}
return `${dateYear}-${dateMonth}`;
}
日期比較與驗證
比較日期
const date1 = new Date('2022-10-23');
const date2 = new Date('2022-10-22');
console.log(date1 > date2); // true
console.log(date1 >= date2); // true
console.log(date1 < date2); // false
console.log(date1 <= date2); // false
檢查日期是否存在
javascript
function isExistDate(dateStr: string): boolean {
let dateObj = dateStr.split('-'); // yyyy-mm-dd
let limitInMonth = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
const theYear = parseInt(dateObj[0]);
const theMonth = parseInt(dateObj[1]);
const theDay = parseInt(dateObj[2]);
const isLeap = new Date(theYear, 1, 29).getDate() === 29; // 閏年檢查
if (isLeap) limitInMonth[1] = 29; // 閏年二月為 29 天
return theDay <= limitInMonth[theMonth - 1];
}