Directory:

  1. End-seeking weirdness: problem statement, problem solution
  2. Chaining simple Ifs: problem statement, no solution available yet.


You may be aware that TI-BASIC's control flow is somewhat unique. Unlike many languages, which are pre-parsed to identify which blocks of code belong to each conditional, TI-BASIC handles control flow line-by-line, as the program is running. You're likely familiar with the fact that you shouldn't put Goto's in If-Then blocks because of a memory leak; this is because of the parser's efforts to keep track of control flow.

To implement the control flow that programmers are familiar with, many statements in TI-BASIC can jump to the nearest End at the same depth as the original statement: If-Then without Else, the Else statement itself, and For( and While if their loop condition is not met.

Because of incorrect assumptions in the TI-BASIC parser, it is possible for two different control flow statements to find the same End when looking for a jump destination. The puzzle is to construct a program where this actually happens. A further puzzle asks if it is possible for three or more different control flow statements to find the same End, etc. No illegal tokens, no crazy parser bugs, etc.

I think the easiest way to keep this puzzle spoiler-free is for you to DM me your solutions, and I'll evaluate them myself.

A final list of people who sent me submissions that passed my tests, in order of my receiving them:

  1. Zeroko, using a different method than my solution.
  2. fghsgh, using the same technique as Zeroko.
  3. commandz, using the same technique as Zeroko.
  4. LogicalJoe, using the same method as my solution.
  5. pi644721, using the same method as my solution.
  6. Wavejumper3, using the same method as my solution.
  7. Zeroko and fghsgh devised a joint solution using the same method as my solution.
  8. Kerm, using the same method as my solution.
  9. Merth, using the same method as my solution but ??? TI-82 only???
  10. linkjt9, using the same method as my solution.


I'll release my solution to this puzzle on 8/10 or after two correct submissions, whichever is later; feel free to discuss your observations in this thread.

A text file with the solution I will post has md5 hash 0a3c7e77d61ecb02cf2f4f8e22a12354.
My observations are this was a fun puzzle! Even though I misinterpreted it the first time around and sent you a wrong submission the second time Razz

Also, my calculator has a broken screen, so I should get a bonus point for that:
Well, this was a lot of fun, and I’m happy to see that so many people submitted solutions (over 80% of the people who submitted solutions eventually produced a correct one, which is fantastic to see!).
Here's a very similar solution to the one that spawned this puzzle (with some pedagogical changes):

Code:
For(K,0,1)
If K
Then
Goto A
End
While 0
Lbl A
Else
End
End

Ignoring the control-flow catastrophe in the middle, let’s take for granted that the outer For( loop runs exactly twice, once with K=0 and once with K=1. Let’s consider each of these cases individually. We’ll first consider the K=1 case, as it is more straightforward than the K=0 case.


Case: K=1

If 1
Then
Goto A

End
While 0
Lbl A
Else
End


The bolded code is the path taken. Remember, the calculator executes the program line by line, so a Lbl/Goto in the middle of an If statement like this does not affect the interpretation of the If statement.
So, stepping through this program:

  • If 1:Then: The calculator sets aside a little piece of memory to remember that it had taken a true If-Then statement.
  • Goto A: the Goto is taken (without disturbing that little piece of memory set aside earlier)
  • Else: The Else checks the little piece of memory to see if it had taken a true If-Then statement (ERR:SYNTAX otherwise), and searches for an End to jump to, which it finds immediately. We won’t yet consider the exact mechanics of searching for an End. This Else is the first conditional to search for and find this End statement.
  • End: The End frees the little piece of memory.
Now, let’s perform the same analysis on the program when K=0.

Case: K=0

If 0
Then

Goto A
End
While 0

Lbl A
Else
End

In this case, both the If statement and the While loop fail to meet their conditions and search for Ends:

  • If 0:Then: The condition fails, so the If statement searches for an End and finds the End after the Goto. Execution continues after this End statement.
  • While 0: This condition also fails, and it finds the End statement after the Else. This While is the second conditional to search for and find this End statement.

The While finding this End is somewhat unexpected, so it’s worth examining exactly what happens when a While or For( loop searches for an End. (n.b. I suppose this isn't strictly necessary to understand the solution. Still, the point of this puzzle was to get you thinking about the minutiae of control flow, so I present it anyway.) It’s straightforward: the While checks the first tokens of successive lines, adding one to a counter if it finds a For(/While/Repeat/If-Then and subtracting one if it encounters an End. The search ends if it encounters an End when the counter is back where it started, and there is no error for reaching the end of the program.

I speculate that at the time when the End-searching was implemented, someone incorrectly assumed that every Else would be preceded by an If-Then (or, more generously, deemed it unnecessary given the additional time-and-space cost of doing it “right”). My less-generous theory is perhaps corroborated by merth’s finding that an isolated Else does not throw an ERR:SYNTAX on specific early TI-82 versions (later pinpointed by Logical to be 8.0 or earlier).

Using my method, you cannot find three statements that find the same End. Specifically, you would need to find three control statements A, B, C such that

  • A, B, C all search for an End
  • A ignores B and C when looking for its End (*)
  • B ignores C when looking for its End

I am thoroughly convinced that the starred condition cannot be met without using DelVar or some undiscovered method.

Using DelVar forms the basis of Zeroko’s first solution. Because While only checks the first token on each line, a While placed on the same line as a DelVar will not be seen (the following elegant solution for three conditionals is due to commandz):

Code:
0
DelVar AWhile 0
Lbl A
DelVar AWhile 0
Lbl B
DelVar AWhile 0
End
Ans+1
If Ans=1:Goto A
If Ans=2:Goto B



The file that generates the hash in my first post follows. (I was concerned that because the program was so short and low-entropy, someone might decide brute-forcing my hash was easier than solving my puzzle, so I added a random string at the end.)

Code:
For(K,0,1
If K
Then
Goto A
End
For(I,1,0
Lbl A
Else
End
End
"em7n0xa136rM9XC6iOZFqDjn6Hl2VpNJETl9JGLzkgPP2ZS5YBKvydCggAT6dSrb
Structure 1 with Goto: 23 bytes
Code:
If 1
Then
Goto 0
Lbl 1
While 0
Lbl 0
Else
End
Goto 1

Structure 2 with For(: 23 bytes

Code:
For(A,0,1
If 1
Then
If A
While 0
Else
End
End


Assuming a reset calculator [all variables start null'd] [as is standard]:

Structure 2 with Ans: 21 bytes

Code:
While 1
If 1
Then
If Ans
While 0
Else
End
1
End



Bonus, structure 2 with IS>(, courtesy of iPhoenix: 25 bytes

Code:
0->A
While 1
If 1
Then
IS>(A,1
While 0
Else
End
End
Here was my submission. It may syntax error on your modern calcs, but if you've got an old one (like 1995), it might work!


Code:

For(A,1,0)
Lbl 0
Else
Pause "IGNORED"
End
A+1->A
If A
Then
Disp A
Goto 0
Using merth's structure we can achieve 17 bytes:
Code:
While 0
Lbl 0
Else
End
If 1
Then
Goto 0
I suppose I can reuse this thread for more control flow puzzles as I devise them.

One advanced use of the If statement looks like this:

Code:
If A
If B
Disp 1
// ignore this comment, formatting is weird
// ignore this comment too

In this code, the Disp is only reached if A is false or B is true. A proof:

Suppose A is false. Then If B is skipped and flow continues directly at the Disp 1. Now suppose A is true. Then If B is checked and Disp 1 is reached if and only if B is true.

What if I repeat this one hundred times (like the following)?

Code:
If L1(1
If L1(2
If L1(3
If L1(4
If L1(5
...
If L1(99
If L1(100
Disp 1

Under what conditions will 1 be printed? You can assume 100=dim(L1 and sum(L1=0)+sum(L1=1)=100. I say that a certain value of L1 allows 1 to be printed if the above program with 100 If statements will execute Disp 1 when L1 has that value.

Your solution should have the following components:

  • A simple, concise description of every value of L1 that will allow a 1 to be printed.
  • A convincing argument for the following two points:
    1. Every list that matches your description will allow a 1 to be printed.
    2. You have found every such list. (i.e. no lists which do not match your description will allow a 1 to be printed)


I think the easiest way to keep this puzzle spoiler-free is for you to DM me your solutions, and I'll evaluate them myself.

A list of people who sent me submissions that passed my tests, in order of receipt (I will probably only update this once or twice daily because I'm rather busy):

  1. kg583
  2. merth
  3. linkjt9
  4. commandz (smallest solution)
  5. LogicalJoe
  6. Zeroko
  7. Michael2_3B
  8. fghsgh


I'll release my solution to this puzzle on October 6th or after two correct submissions, whichever is later; feel free to discuss your observations in this thread.
Put me on da list cause I cracked it!
well this is actually quite complicated, I've been trying it for an hour, and I see how it works, I just can't seem to explain part of it.
Fun puzzle indeed. Pretty simple when you realize the pattern
  
Register to Join the Conversation
Have your own thoughts to add to this or any other topic? Want to ask a question, offer a suggestion, share your own programs and projects, upload a file to the file archives, get help with calculator and computer programming, or simply chat with like-minded coders and tech and calculator enthusiasts via the site-wide AJAX SAX widget? Registration for a free Cemetech account only takes a minute.

» Go to Registration page
Page 1 of 1
» All times are UTC - 5 Hours
 
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum

 

Advertisement