Find the next number in the pattern

Write a program, that takes 5 numbers as input and outputs the next number in the pattern.

Heres a text file with 1835 test patterns, containing 6 numbers separated by commas each line. Using the first 5 numbers calculate the 6th number and then check if it matches. You must get all the test cases correct.

There are 3 types of patterns:

1. xn = xn-1+k

2. xn = xn-1*k

3. xn = xn-1^2

The first x value and k were chosen randomly between a set range to create the pattern sample file.

This is code-golf, lowest number of bytes to get all of the test cases correct wins.

• It seems fairly easy to get 100%. Is there a tiebreak?
– xnor
Sep 18 '14 at 5:57
• The tiebreaker should be the length of the code because any solution can easily be O(n) time, i'll edit the question. Well this is just a duplicate of the other question then, should it be closed? Sep 18 '14 at 6:43
• In that case, why don't you make it code golf and require getting all the test cases right?
– xnor
Sep 18 '14 at 6:46
• Its pretty disappointing there are no trick rows; contestants are getting a perfect score by checking just the first three ints, and there's no divide-by-zeros being thrown either.
– Will
Sep 18 '14 at 7:53
• -1 for doing big changes in the scoring system. Please use the sandbox the next time Sep 18 '14 at 8:39

Python 2: 55 bytes

f=lambda a,b,c,d,e:e+c-d*2and e*e/d**(d*d==e*c)or e*2-d


We check for the three cases as follows:

1. Check for arithmetic sequence: If e+c==d+d, output e+e-d
2. Check for geometric sequence: If e*c==d*d, output e*e/d
3. Otherwise, squared sequence: Output e*e.

Case 3 is used as the else-case to avoid the more-lengthy checking for successive squaring.

Case 1 is checked first, with Boolean short-circuiting to avoid checking Case 2 after a success, as this causes an error when d=0. There's a test case of all zeroes, so we can't cheat this by picking another position in place of d.

Afterwards, we can treat both Cases 2 and 3, since there's no risk of a divide-by-0 error. Noting that the choices are similar (e*e vs e*e/d), we combine them with an arithmetic expression by dividing by either d**1 for Case 3 or d**0 for Case 2. Although this division produces an integer value, we must use Python 2 (or //) to avoid float errors that case the largest-output test case to fail.

Thanks to @Will for inspiration on the code structure and a very-helpful test framework.

• Still, like the multiply instead of and :)
– Will
Sep 21 '14 at 9:39

Python all right, 72 7475 chars

p=lambda i,j,k,l,m:j-i!=k-j and(k==j*j==j*i*i and m*m or m*l/k)or m+j-i


Thx to xnor for showing me the if/else to and/or trick and golfing off a char :)

Thx to flornquake for fixing the k==j*j==j*i*i and saving another two chars :)

Actually, it gets one wrong... but that's a bug in the test patterns which was acknowledged yesterday but still not fixed.

Testing code, hopefully useful for all competitors to test with:

def check(func,title):
right = 0
print "===", title, "==="
for i,test in enumerate(open('patterns.txt')):
test = map(int,test.split(','))
try:
got, expected = func(*test[:5]), test[5]
except Exception as e:
got = e
if got != expected:
print "ERROR on line %d: %s != %d" % (i, got, expected)
print " test :", ", ".join(map(str,test))
plus = multi = cube = str(test[0])
for i in range(1, 6):
plus += ", %d" % (test[i-1]+(test[1]-test[0]))
multi += ", %s" % ((test[i-1]*(test[1]/test[0])) if test[0] else "DivZero")
cube += ", %d" % (test[i-1]**2)
print " as + :", plus
print " as * :", multi
print " as ^2:", cube
else:
right += 1
print right, "out of", i+1, "right!"


says:

ERROR on line 19: 23283064365386962890625 != 3273344365508751233
test : 5, 25, 625, 390625, 152587890625, 3273344365508751233
as + : 5, 25, 45, 645, 390645, 152587890645
as * : 5, 25, 125, 3125, 1953125, 762939453125
as ^2: 5, 25, 625, 390625, 152587890625, 23283064365386962890625
1834 out of 1835 right!

• You can usually save chars from the if/else ternany operator using the and/or trick: codegolf.stackexchange.com/a/57/20260
– xnor
Sep 19 '14 at 8:33
• I had deleted my suggestion of k==j*j==i**4 on realizing it fails for 1, -1, 1, -1, 1, -1, but it turns out you can dodge it by using j,k,l instead, which changes the parity. I assume it's allowed to take advantage of a coincidental hole in the test cases?
– xnor
Sep 19 '14 at 8:56
• @xnor thx for the encouragement and leads :) I don't really want to take advantage of holes in the test cases. And the I didn't know that neat and/or trick! But its not applicable for this particular problem because the correct prediction may be falsy, e.g. -10, -8, -6, -4, -2, 0. Still neat to learn.
– Will
Sep 19 '14 at 8:59
• Hmm, I think and/or should just work, independent of the truthiness of the output. Let's try to fix it. Can you check that you converted a if b else c to b and a or c? And also that the two of it are nested right and perhaps parenthesized to parse right? If it still doesn't work, could you please tell me what you have.
– xnor
Sep 19 '14 at 9:04
• @xnor q=lambda i,j,k,l,m:j-i==k-j and m+j-i or(j==i*i)&(k==j*j)and m*m or m*l/k is how I wrote it.
– Will
Sep 19 '14 at 9:05

C# - 1835

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;

namespace pattern
{
class Program
{
static void Main(string[] args)
{
string[] lines = File.ReadAllLines("in.txt");
int matches = 0;
for(int i = 0; i < lines.Length; i++)
{
long[] numbers = lines[i].Split(',').Select(a=>long.Parse(a)).ToArray();

long nextnum = 0;
if(numbers[1]-numbers[0]==numbers[2]-numbers[1])
nextnum = numbers[numbers.Length-2]+(numbers[1]-numbers[0]);
else if(numbers[1]/numbers[0]==numbers[2]/numbers[1])
nextnum = numbers[numbers.Length-2]*(numbers[1]/numbers[0]);
else if(numbers[1] == numbers[0]*numbers[0])
nextnum = numbers[numbers.Length-2]*numbers[numbers.Length-2];
if(nextnum == numbers[numbers.Length-1])
matches++;
}
Console.WriteLine(matches + " matches found!");
}
}
}


This is obviously not golfed at all, but it finds all numbers eventually. It just prints how many matches it found, but you could potentially display all found numbers, only non-matches, etc...

(This is conceptually very similar to Beta Decay's answer, just a little bit more complicated)

• I love C#, it is like a mixture of everything, it has lambdas, anonymous delegates, LINQ, and a bunch of other features haha, not exactly fit for golfing though :P Sep 18 '14 at 6:47
• Yeah, C# is great for some purposes. Well, like I said, I didn't golf this a whole lot :P Sep 18 '14 at 7:37

Python 3 -1833

Length 198 chars

Now updated to conform to the rules.

m=0
for i in open('s'):
if','in i:
i,j,k,l=list(map(int,i.split(',')[2:]))
if j-i==k-j:
if k+(j-i)==l:m+=1
elif j/i==k/j:
if k*(j/i)==l:m+=1
elif i**2==j:
if k**2==l:m+=1
print(m)

• You can golf this a lot (the rules are changing under us and code size is now important) e.g. for i in open('s.txt'): and unpacking the first three ints in the split etc.
– Will
Sep 18 '14 at 6:56
• here's a 112 byte version, but I miss tricks: gist.github.com/williame/f8ae068ff7e658cde28f
– Will
Sep 18 '14 at 7:05
• I know this has been accepted by the poster, so must meet their criteria of correctness, but it seems to be overlooking the requirement Using the first 5 numbers calculate the 6th number and then check if it matches?
– Will
Sep 18 '14 at 8:11
• i**2 is longer than i*i. Sep 18 '14 at 15:19
• Python can read from files without a .txt extension (I just tested this). The name of the file was not specified in the problem, so you should shave off four characters by naming it a single letter. for i in open('s'):, assuming the file was named "s". Sep 18 '14 at 15:24

TI-BASIC, 120117 136

Prompts for input and returns the output.

Input L1:0:If not(L1(5:Stop
If L1(5)-L1(4)=L1(4)-L1(3:L1(5)+(L1(5)-L1(4
If L1(5)/L1(4)=L1(4)/L1(3:L1(5)(L1(5)/L1(4
If L1(4)²=L1(5:L1(5)²


Edit: Fixed divide by zero error.