Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Challenge: Compute the number of Tuesdays since a given date
#21
Hrmm, I couldn't post this very simple solution of mine earlier, but here it is still:

Code:
' =================================================
' Day Counter
'
' By Neo Deus Ex Machina
' Simplest form I could make up ... ;)
'
' Saturday 19th of June 2004
' =================================================

DECLARE SUB InitData ()
DECLARE SUB GetInput ()
DECLARE SUB Calculate ()

DEFINT A-Z
'$DYNAMIC

DIM SHARED DaysPerMonth(1 TO 12) AS INTEGER
DIM SHARED MonthsName(1 TO 12) AS STRING
DIM SHARED DaysName(1 TO 7) AS STRING

DIM SHARED TodayDay AS INTEGER
DIM SHARED TodayMonth AS INTEGER
DIM SHARED TodayYear AS INTEGER
DIM SHARED NowIndex AS INTEGER
DIM SHARED NowDay AS INTEGER
DIM SHARED NowMonth AS INTEGER
DIM SHARED NowYear AS INTEGER
DIM SHARED NumReqDays AS LONG
DIM SHARED DayCount AS INTEGER

'NOTE:
' 1-1-1900 was a Sunday (backtracked)

InitData
GetInput
Calculate

PRINT
SYSTEM

SUB Calculate
    NowDay = 1
    NowMonth = 1
    NowYear = 1900
    NowIndex = 7
    NumReqDays = 0

    IF INT(NowYear / 4) * 4 = NowYear THEN DaysPerMonth(2) = 29 ELSE DaysPerMonth(2) = 28
    IF NowIndex = DayCount THEN NumReqDays = NumReqDays + 1
    DO UNTIL NowDay >= TodayDay AND NowMonth >= TodayMonth AND NowYear >= TodayYear
                NowDay = NowDay + 1

                IF NowDay > DaysPerMonth(NowMonth) THEN
                    NowDay = 1
                    NowMonth = NowMonth + 1
                    IF NowMonth > 12 THEN
                        NowMonth = 1
                        NowYear = NowYear + 1
                        IF INT(NowYear / 4) * 4 = NowYear THEN DaysPerMonth(2) = 29 ELSE DaysPerMonth(2) = 28
                    END IF
                END IF

                NowIndex = NowIndex + 1
                IF NowIndex > 7 THEN NowIndex = 1

                IF NowIndex = DayCount THEN NumReqDays = NumReqDays + 1
    LOOP

    CLS
    BackPrint$ = ""
    IF NowDay MOD 10 = 1 THEN
        BackPrint$ = "st"
    ELSEIF NowDay MOD 10 = 2 THEN
        BackPrint$ = "nd"
    ELSEIF NowDay MOD 10 = 3 THEN
        BackPrint$ = "rd"
    ELSE
        BackPrint$ = "th"
    END IF
    PRINT NumReqDays; DaysName(DayCount) + "s had passed since Sunday 1st of January 1900 up to"
    PRINT " and including "; DaysName(NowIndex); STR$(NowDay) + BackPrint$ + " of "; MonthsName(NowMonth); NowYear
END SUB

SUB InitData
    DaysPerMonth(1) = 31
    DaysPerMonth(2) = 28
    DaysPerMonth(3) = 31
    DaysPerMonth(4) = 30
    DaysPerMonth(5) = 31
    DaysPerMonth(6) = 30
    DaysPerMonth(7) = 31
    DaysPerMonth(8) = 31
    DaysPerMonth(9) = 30
    DaysPerMonth(10) = 31
    DaysPerMonth(11) = 30
    DaysPerMonth(12) = 31

    MonthsName(1) = "January"
    MonthsName(2) = "February"
    MonthsName(3) = "March"
    MonthsName(4) = "April"
    MonthsName(5) = "May"
    MonthsName(6) = "June"
    MonthsName(7) = "July"
    MonthsName(8) = "August"
    MonthsName(9) = "September"
    MonthsName(10) = "October"
    MonthsName(11) = "November"
    MonthsName(12) = "December"

    DaysName(1) = "Monday"
    DaysName(2) = "Tuesday"
    DaysName(3) = "Wednesday"
    DaysName(4) = "Thursday"
    DaysName(5) = "Friday"
    DaysName(6) = "Saturday"
    DaysName(7) = "Sunday"
END SUB

SUB GetInput
    PRINT "This program can give the number of specific days passed up to a given date"
    PRINT
    DO
        PRINT "Enter the year (>= 1900 and <= 32000):"
        INPUT "", TYEAR$
    LOOP UNTIL VAL(TYEAR$) >= 1900 AND VAL(TYEAR$) <= 32000
    PRINT
    DO
        PRINT "Enter the month (>= 1 and <= 12):"
        INPUT "", TMONTH$
    LOOP UNTIL VAL(TMONTH$) >= 1 AND VAL(TMONTH$) <= 12
    PRINT
    DO
        PRINT "Enter the day (>= 1 and <= 31 and existing):"
        INPUT "", TDAY$
    LOOP UNTIL VAL(TDAY$) >= 1 AND VAL(TDAY$) <= 31
    PRINT
    DO
        EXIST = 0

        PRINT "Enter the name of the day to count (e.g. tuesday) in English:"
        INPUT "", DAY$

        FOR I = 1 TO 7
            IF LCASE$(LTRIM$(RTRIM$(DAY$))) = LCASE$(LTRIM$(RTRIM$(DaysName(I)))) THEN EXIST = I
        NEXT I
    LOOP UNTIL EXIST > 0

    TodayDay = VAL(TDAY$)
    TodayMonth = VAL(TMONTH$)
    TodayYear = VAL(TYEAR$)
    DayCount = EXIST
END SUB
Reply
#22
Neo, looks interesting. Give me a few days to test it out.

Two comments:
(1)
' 1-1-1900 was a Sunday (backtracked)
NO, IT WAS A MONDAY.

(2) IF INT(NowYear / 4) * 4
THIS IS NOT A VERY GOOD WAY TO CHECK FOR LEAP YEAR. FOR EXAMPLE, THIS CODE WOULD CONSIDER 1900 AS A LEAP YEAR, WHICH IT WAS NOT. SEE THË "ISLEAPYEAR" FUNCTION AND COMMENTS AT THE END OF MY POSTED SOLUTION ABOVE.
*****
Reply
#23
Quote:(1)
' 1-1-1900 was a Sunday (backtracked)
NO, IT WAS A MONDAY.
This is caused by my explaination at comment (2).

Quote:(2) IF INT(NowYear / 4) * 4
THIS IS NOT A VERY GOOD WAY TO CHECK FOR LEAP YEAR. FOR EXAMPLE, THIS CODE WOULD CONSIDER 1900 AS A LEAP YEAR, WHICH IT WAS NOT. SEE THË "ISLEAPYEAR" FUNCTION AND COMMENTS AT THE END OF MY POSTED SOLUTION ABOVE.
*****
Hrmm, I thought every year, multiplier of 4 was a leap year. (read your IsLeapYear)... hrmmm... ok right. So 1900 was not... that means 1-1-1900 wasn't a Sunday but a Monday indeed (counted 1 day extra: 29-2-1900). To solve this problem, do this:

Replace:
Code:
IF INT(NowYear / 4) * 4 = NowYear THEN DaysPerMonth(2) = 29 ELSE DaysPerMonth(2) = 28
by:
Code:
IF (NowYear MOD 4 = 0 AND NowYear MOD 100 <> 0) OR (NowYear MOD 400 = 0) THEN DaysPerMonth(2) = 29 ELSE DaysPerMonth(2) = 28
(didn't even know this but I learnt from your function Wink)
Reply
#24
Neo,

Actually I found the rule in my Webster's dictionary under leap year. If a year is a multiple of 100, although it as a multiple of 4, in order to be a leap year it has to be a multiple of 400. Example: the year 2100 will not be a leap year either.

Recently, I saw a new rule added to leap year. I'm not sure exactly but it has to do with being a multiple of 4000. A little too far in the future for me yet, so I haven't bothered to implement it into my leap year algorithm.

BTW, my main computer is down so I haven't had a chance to test your posted solution. I'm writing this from my daughter's machine which does not have any of my QB stuff. Give me a few more days.
*****
Reply
#25
Ok Neo, tried your routine and discovered that you got the specifications mixed up.
The original specs said: Starting from a given date, no earlier than 1/1/1900, compute the number of Tuesdays that have transpired up to but not including today.

The specs that you programmed are: Compute the number of Tuesdays from 1/1/1900 up to and including an input date.

Close, but an entirely different idea. Anyway, you'll be happy to know that it computed 5452 Tuesdays from 1/1/1900 to today 6/28/2004 --- which is correct.

So, except for the leap year error, your other date computations seem to be working pretty good.

Try fixing the program to use the original specs. I'd like to see how it performs then.
*****
Reply


Forum Jump:


Users browsing this thread: 1 Guest(s)