Форма Microsoft Access, в которой используется «Код даты» для автоматического создания, но всегда с опозданием на 1 неделю - PullRequest
1 голос
/ 16 июня 2020

Я плохо владею Access и пытаюсь понять, почему поле кода даты не распространяется правильно. Поле Скриншот кода даты отображается как YYWWDD (последние две цифры года, номер недели в году и день рабочей недели (понедельник = 1 - пятница = 5), но для последних двух лет Номер недели в году постоянно отставал на 1 неделю. Как видно на скриншоте Код даты 20242, это фактически 25 неделя с первой недели января.

код на странице свойств выглядит следующим образом:

=IIf(IsNull([DaySelected]),IIf(Len(Format(Date(),"ww",2,3))=1,Format(Date(),"yy") & "0" & Format(Date(),"ww w",2,3),Format(Date(),"yywww ",2,3)),IIf(Len(Format(Date(),"ww",2,3))=1,Format(Date(),"yy") & "0" & Format(Date(),"ww",2,3) & [DaySelected],Format(Date(),"yyww",2,3) & [DaySelected]))

Любая помощь будет принята с благодарностью.

1 Ответ

0 голосов
/ 16 июня 2020

Проблема в том, что год является годом ISO 8601, а не календарным годом, и для получения истинного номера недели ISO 8601 требуется настраиваемая функция:

' Returns the ISO 8601 week of a date.
' The related ISO year is returned by ref.
'
' 2016-01-06. Gustav Brock, Cactus Data ApS, CPH.
'
Public Function Week( _
    ByVal Date1 As Date, _
    Optional ByRef IsoYear As Integer) _
    As Integer

    Const MaxWeekValue           As Integer = 53
    Const MinWeekValue           As Integer = 1
    Const MaxMonthValue          As Integer = 12
    Const MinMonthValue          As Integer = 1

    Dim Month       As Integer
    Dim Interval    As String
    Dim Result      As Integer

    Interval = "ww"

    Month = VBA.Month(Date1)
    ' Initially, set the ISO year to the calendar year.
    IsoYear = VBA.Year(Date1)

    Result = DatePart(Interval, Date1, vbMonday, vbFirstFourDays)
    If Result = MaxWeekValue Then
        If DatePart(Interval, DateAdd(Interval, 1, Date1), vbMonday, vbFirstFourDays) = MinWeekValue Then
            ' OK. The next week is the first week of the following year.
        Else
            ' This is really the first week of the next ISO year.
            ' Correct for DatePart bug.
            Result = MinWeekValue
        End If
    End If

    ' Adjust year where week number belongs to next or previous year.
    If Month = MinMonthValue Then
        If Result >= MaxWeekValue - 1 Then
            ' This is an early date of January belonging to the last week of the previous ISO year.
            IsoYear = IsoYear - 1
        End If
    ElseIf Month = MaxMonthValue Then
        If Result = MinWeekValue Then
            ' This is a late date of December belonging to the first week of the next ISO year.
            IsoYear = IsoYear + 1
        End If
    End If

    ' IsoYear is returned by reference.
    Week = Result

End Function

Затем создайте простой пользовательский функция для генерации номера дня недели-года:

Public Function FormatWeekDayIso8601(ByVal DaySelected As Integer) As String

    Dim Result              As String

    Dim IsoYear As Integer
    Dim IsoWeek As Integer

    IsoWeek = Week(Date, IsoYear)
    Result = _
        CStr(IsoYear Mod 100) & _
        VBA.Format(IsoWeek, String(2, "0")) & _
        CStr(DaySelected)

    FormatWeekDayIso8601 = Result

End Function

Теперь используйте это так:

=FormatWeekDayIso8601(Nz([DaySelected],1))
...