_TITLE "3 Snacky Friends, a donkey, and apples"

' This program exported from BASIC Anywhere Machine (Version [5.2.3].[2024.07.14.16.44]) on 2024.08.04 at 01:48 (Coordinated Universal Time)

' This program by Charlie Veniot is in response to the programming challenge by "sVB"
' shared with the "BASIC Programming Language" Facebook group
' (https://www.facebook.com/share/p/nn3AsgznQdLr8rMB/)

' This program looks at every possible morning scenario starting at 1 apple per friend,
'   incrementing the number of apples per friend by one
'   each loop and looping to infinity
' For each morning scenario, we go backwards to figure out the number of apples
' (including fractions of apples) per snack time
'   * how many apples must there have been for the 3rd snacktime
'   * then how many apples must there have been for the 2nd snacktime
'   * then how many apples must there have been for the 1st snacktime
' If any scenario has total apples at any snacktime that is not a whole number, that
'   scenario is rejected

' Program sections:
'   🟠 Declarations and Initialization
'   🟠 Main program
'   🟠 GOSUB Routines

' -−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−
' 🟠 Declarations and Initialization

  OPTION EXPLICIT

  DIM i% = 1          ' The number of apples per friend available at morning time
  DIM PrintCount% = 0 ' Track count of valid scenarios printed for reprinting headline info
  DIM bFound AS BYTE  ' A "fake" boolean; TRUE = -1, FALSE = 0
  DIM GmApples#       ' Good morning apple count before eating
  DIM S3Apples#       ' Snacktime 3 apple count before eating
  DIM S2Apples#       ' Snacktime 2 apple count before eating
  DIM S1Apples#       ' Snacktime 1 apple count before eating

  DEF FN FinalApplesTotal#(v%) = v% * 3 + 1
      ' What are the total number of apples available at morning time?
      '   Whatever it is, there has to be 1 apple for the donkey and
      '   a remaining number of apples that can be equally split among the three friends
      ' v% = number of whole apples per friend available at morning time
      ' multiply by the three friends for total apples that can be evenly split, then add
      '   1 apple for the donkey
  DEF FN SnacktimeApplesTotal#(v%) = v% / 2 * 3 + 1
      ' v% is the total number of apples which can be equally divided between two friends
      '   after a snacking friend gave 1 apple to the donkey
      '   and that friend consumed one third of the remaining apples (leaving equal share
      '   of apples for the other two friends)
      ' divide v% by two to find out the equal share per friend
      ' multiply by three to get the total for the friends
      ' then add 1 for the donkey
      ' the result is the total number of apples existing before the friend can eat
  DEF FN AllWholeSnacktimeCounts% = FRAC( (S3Apples# - 1) / 3 ) = 0 _
                                AND FRAC( (S2Apples# - 1) / 3 ) = 0 _
                                AND FRAC( (S1Apples# - 1) / 3 ) = 0
  DEF FN PrintGroupFmt$( Moment$, Apples# ) = "[" + Moment$ + "]" _
                                + " A:" + STR$( Apples# ) _
                                + " S:" + STR$( ( ( Apples# ) - 1 ) / 3 ) + " D:1 "
  
  SCREEN _NEWIMAGE( 960, 184, 0 )
  COLOR 14

' -−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−
' 🟠 Main program

PRINT "Once upon a time, 3 friends bought apples and carried them on a donkey."
PRINT "When night came, they decided to sleep in the forest."
PRINT
PRINT "The first friend woke up hungry at midnight, so he divided the apples into three equal shares."
PRINT "The one extra remaining apple, he gave it to the donkey.  He then ate his share and went back to sleep."
PRINT
PRINT "A while later, the second friend woke up hungry, so he divided the remaining apples into three equal shares."
PRINT "The one extra remaining apple, he gave it to the donkey.  He then ate his share and went back to sleep."
PRINT
PRINT "A while later, the third friend woke up hungry, so he divided the remaining apples into three equal shares."
PRINT "The one extra remaining apple, he gave it to the donkey.  He then ate his share and went back to sleep."
PRINT
PRINT "In the morning, the 3 friends woke up hungry, so they divided the remaining apples into three equal shares."
PRINT "The one extra remaining apple, they gave it to the donkey.  They then ate each of their share."
PRINT
PRINT "How many apples did they initially buy, and how many apples did each of them eat?"
PRINT
PRINT "Click/touch the screen to continue."
SLEEP
CLS
PRINT "Pause the program at any time by clicking/touching and holding the click/touch until you want the program to continue."
PRINT
PRINT "Click/touch the screen to start evaluating the possibilities."
SLEEP
CLS

➔10_ShowHeadingLine:
    COLOR 15
    IF PrintCount% > 0 THEN PRINT "Click/Touch the screen to continue"; : SLEEP : PRINT
    PRINT "A = Total Apple Count at Time (shown between [ and ]); S = Apple Share Count per Friend; D = Apple for Donkey"
    PRINT
    COLOR 14
    
➔20_ResolveNextLegitScenario:
    IF _MOUSEBUTTON THEN WHILE _MOUSEBUTTON : WEND
    GOSUB 🍎100_SetAppleCountPerTime

    IF AllWholeSnacktimeCounts%() THEN
       bFound = TRUE : PrintCount% += 1
       PRINT PrintGroupFmt$( "Morning", GmApples# ) _
           + PrintGroupFmt$( "Snack 3", S3Apples# ) _
           + PrintGroupFmt$( "Snack 2", S2Apples# ) _
           + PrintGroupFmt$( "Snack 1", S1Apples# )
       PRINT "Friend 3 ate " + ( ( ( GmApples# - 1 ) + ( S3Apples# - 1 ) ) / 3 ) + " apples."
       PRINT "Friend 2 ate " + ( ( ( GmApples# - 1 ) + ( S2Apples# - 1 ) ) / 3 ) + " apples."
       PRINT "Friend 1 ate " + ( ( ( GmApples# - 1 ) + ( S1Apples# - 1 ) ) / 3 ) + " apples."
       PRINT
    ELSE
      bFound = FALSE
    END IF
    
    SLEEP 0.2
    i% += 1
    IF bFound AND ( PrintCount% MOD 4 = 0 ) THEN GOTO ➔10_ShowHeadingLine
GOTO ➔20_ResolveNextLegitScenario

END

' -−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−-−
' 🟠 GOSUB Routines

🍎100_SetAppleCountPerTime:
    GmApples# = FinalApplesTotal#( i% )
    S3Apples# = SnacktimeApplesTotal#( GmApples# )
    S2Apples# = SnacktimeApplesTotal#( S3Apples# )
    S1Apples# = SnacktimeApplesTotal#( S2Apples# )
RETURN