2016-12-26 20 views
-2

GOの相対日時を解析するにはどうすればよいですか?相対日付の相対日付解析

例:

today at 9:17 AM 
yesterday at 9:58 PM 
Saturday at 9:44 PM 
Wednesday at 11:01 AM 

ので、フォーマットはDAY (in the past) at TIMEです。さらになし

だけMonday

const longForm = "Monday at 3:04 PM" 
t, _ := time.Parse(longForm, "Saturday at 3:50 PM") 
fmt.Println(t) 

demo

時間が正しく解析されていますが、日/日付が無視されます...

+0

'Monday'がさらに日付参照することなく、パーサの目には無意味であるので、それは破棄されます。どの月曜日ですか?あなたはもっと洗練されたパーサを書く必要はありません。 –

+0

@Not_a_Golfer:過去の最初の月曜日、私はすでに、次のような質問にそれを書いています。「フォーマットは「過去(TIME)」です。私は次の例を試しました: ' –

+0

はい、パーサーにそれを伝えることはできますか?いいえ! –

答えて

1

が私のコメントに拡大:私は、次の例を試してみましたパーサの目には日付の参照は無意味なので、破棄されます。どの月曜日ですか?パーサーは厳密でファジーではありません。月曜日が現在の週を指すと仮定すると、そのようなパーサーが行うことはできません。あなたはもっと洗練されたパーサを書く必要はありません。

だから、これらの線に沿ってでなければならない - 実際の日付に対するファジー日を変換の機能を、元の表現であることを置き換え、そして全体を解析し、別の1:

const dateFormat = "2006-01-02" 
const longForm = "2006-01-02 at 3:04 PM" 

func parseFuzzyDate(fuzzyTime string) (time.Time, error) { 

    formattedTime, err := parseDayAndReplaceIt(fuzzyTime) 
    if err != nil { 
     return nil, err 
    } 

    return time.Parse(longForm, formattedTime) 
} 

と2番目の関数は、ファジー時間を取得し、その日を見つけ、それを解析して返します。私は何をすべきか、コメントに書き込み、それを実装するつもりはない:

func parseDayAndReplaceIt(fuzzyTime string) (string, error) { 
    // 1. Extract the day 

    // 2. Parse weekday names to relative time 

    // 3. if it's not a weekday name, parse things like "tomorrow" "yesterday" 

    // 4. replace the day string in the original fuzzyTime with a formatted date that the parser can understand 

    // 5. return the formatted date 
} 
0

私はしばらく前に書いたものを微調整して、このサンプルコードにそれを集約:

func lastDateOf(targetDay time.Weekday, timeOfDay time.Time) time.Time { 
    const oneDay = 24 * time.Hour 
    var dayIndex time.Duration 

    //dayIndex -= oneDay 
    for { 
     if time.Now().Add(dayIndex).Weekday() == targetDay { 
      y, m, d := time.Now().Add(dayIndex).Date() 
      return timeOfDay.AddDate(y, int(m)-1, d-1) 
     } 
     dayIndex -= oneDay 
    } 
} 

それは、前のtargetDayの現在の日付をtimeOfDayに追加します。timeOfDayは時、分、秒で構成され、年、月、日のゼロ時間値は適切な回答を与えます。

これはあまり柔軟ではありませんが、あなたの例が合理的にうまくいくと私は信じています。それは "明日"、 "昨日"または "次の土曜日"のような相対的な用語に対処していません。

実行可能バージョンplaygroundです。

0

カスタムパーサー:

func RelativeDateParse(s string) (time.Time, error) { 
    for n := 0; n < 7; n++ { 
     day := time.Now().AddDate(0, 0, -n) 
     dayName := day.Format("Monday") 
     switch n { 
     case 0: 
      dayName = "today" 
     case 1: 
      dayName = "yesterday" 
     } 
     s = strings.Replace(s, dayName + " at", day.Format("2006-01-02"), -1) 
    } 
    return time.Parse("2006-01-02 3:04 PM", s) 
} 

demo

関連する問題