日付を漢数字和暦表記の文字列に変換する


NSDateから和暦の漢数字日付表記を得たかった。

平成元年一月七日
平成二十九年十二月二十三日

NSDateFormatterのみでは実現が難しそうだったので、漢数字変換に対応しているNSNumberFormatterとの合わせ技で解決した。
ついでに台湾の中華民国歴にも対応してみた。縦書きにすると漢数字が映える。

Dateから漢数字和暦表記の文字列を得るextension
import Cocoa

// Calendarの生成が重いので、キャッシュしておくなりが良いかもしれない
let calJapanese = Calendar(identifier: .japanese)
let calTaiwanese = Calendar(identifier: .republicOfChina)

extension Date {

    /// 漢数字日付を得る
    func kanjinizedDateString(withLocale locale: Locale, calendar: Calendar) -> String {
        let sfx_year = "年"
        let sfx_month = "月"
        let sfx_day = "日"
        let firstYear = "元"
        let none = "ー"

        func kanjinize(_ num: Int?) -> String {
            guard let num = num else {return none}

            let nf = NumberFormatter()
            nf.locale = locale
            nf.numberStyle = .spellOut // 漢数字表記
            return nf.string(from: NSNumber(value: num)) ?? none
        }

        // 元号を得る
        let df = DateFormatter()
        df.locale = locale
        df.calendar = calendar
        df.dateFormat = "G"
        let era = df.string(from: self)

        // 一年は「元年」に置き換える
        let comps = calendar.dateComponents([.year, .month, .day], from: self)
        let yearStr = (comps.year ?? 0) > 1 ? kanjinize(comps.year) : firstYear
        let monthStr = kanjinize(comps.month)
        let dayStr = kanjinize(comps.day)

        return era + yearStr + sfx_year + monthStr + sfx_month + dayStr + sfx_day
    }

    /// 漢数字和暦日付を得る
    func japaneseKanjinizedDateString() -> String {
        let locale = Locale(identifier: "ja")
        return kanjinizedDateString(withLocale: locale, calendar: calJapanese)
    }

    /// 漢数字中華民国暦日付を得る
    func taiwaneseHanzinizedDateString() -> String {
        let locale = Locale(identifier: "zh-tw")
        return kanjinizedDateString(withLocale: locale, calendar: calTaiwanese)
    }

}
使い方
let date = Date()
date.japaneseKanjinizedDateString()
date.taiwaneseHanzinizedDateString()
"平成二十九年七月二十八日"
"民國一百零六年七月二十八日"

Playground