Welcome to HBH! If you have tried to register and didn't get a verification email, please using the following link to resend the verification email.

Project Euler: Problem 28, coded in python


thehare's Avatar
Member
0 0

Hello everyone, I lately have had my spark for programming reappear (had started to learn python a while back) and have found a website called project euler that gives mathematical problems to be solved using your programming skills.

I have been doing decently until I hit a wall, I believe the mathematical foundation behind my code is correct, but it is not giving me the correct answer.

The question can be found here: http://projecteuler.net/problem=28

Here is the code that I used to find the answer (like i said before, I am very new to the programming scene but criticism is always welcome)

diagA = []
diagB = []
a = 1
a_change = 2
b = 1
b_change = 4
b_counter = 1


while loop == 1:
    if a <= 1002001:           # the largest number in the first diagonal
        a=a_change + a         # finds the next number in the diagonal
        a_change=a_change+2    # changes the amount the next number in the diagonal increases, according to the mathimatical rule found 
        diagA[1:1]=[a]         # records new number in the list
        print "yes"            # just used this to show program hasnt frozen
    else:
        print "Done A"          #shows that diagonal A is done and switches loop to begin code for diagonal B
        loop = 2
        

while loop == 2:
    if b <=1001001:         # the largest number in the second diagonal
        b=b_change+b         # finds the next number in the diagonal
        b_counter = b_counter + 1    #using counter because it was found that the amount of change increases every odd interval
        if b_counter%2 !=0:         # When the interval is odd this piece of code activates
            b_change = b_change+4   # changes the amount the next number in the diagonal increases, according to the mathimatical rule found 
        else:
            pass
        diagB[1:1]=[b]          # records new number in the list
        print "yes b"

    else:
        print "done b"
        loop = 3            #ends code
        print ""
        print diagA         #prints all numbers in Diagonal A (just to ensure that the numbers are correct
        print ""
        print diagB         #prints all numbers in Diagonal B (just to ensure that the numbers are correct
        print ""
        print sum(diagA + diagB)    ######### prints the sum off all numbers in the diagonal , THIS IS WHERE I BELIEVE THE ERROR IS######        
        

thehare's Avatar
Member
0 0

And never mind…..found my own error.

Program added one more number than it should have lol


Arabian's Avatar
Member
0 0

Another Project Euler enthusiast? Great!

Hit us up in the IRC sometime. Lots of us do or are down to do Euler problems. I'm on ~58


thehare's Avatar
Member
0 0

Haha, ya I just found them, but I've been doing them for the last few hours non stop (but because my programming ability is…..limited, progress is slow lol).

I've done 1-3 + 28, I absolutely love doing the challenges, they really help you learn the language (python for me) I find.


Arabian's Avatar
Member
0 0

I do them as exercises for languages, and have finished at least one of them in Perl, Python, C, C++, Haskell, Lisp, and Java.


NotMyFault's Avatar
Member
0 0

You're all working too hard ;)

#include <iostream>
using namespace std;

int main() {
	long long int answer = 1;

	for(int i=3; i<=1001; i+=2)
		answer += ( 4*((i*i)-(((i-1)/2)-1+i)) );

	cout << answer << endl;
	return 0;
}

exploit the fact that the spirals expand predictably.


ShadowGate's Avatar
Member
0 0

Nice elegant solution, good work. It is not often you see an example in c that is smaller then a python counter part.

I tried converting you're version to python. Although python gets rid of the boilerplate I feel like its a bit more hackish then the c version. Also of course in terms of time and memory c is faster and takes less memory.

Python: time: 0.02s memory: 4676 kB C: time: 0.01s memory: 2724 kB

for i in range(3, 1002):
    if i % 2 != 0:
        answer += (4*((i*i)-(((i-1)/2)-1+i)))
print("Answer: " + str(answer))```

stranac's Avatar
Member
0 0

@ShadowGate:

You can use a step argument in range like this:

for i in range(3, 1002, 2):

Also, the sum() built-in function might be faster than manual addition.

And there is no need to convert the answer to string. You can do it with string formatting or, in this simple case, just passing multiple arguments to print():

print('Answer:', answer)

Arabian's Avatar
Member
0 0

NotMyFault wrote: You're all working too hard ;)

#include <iostream>
using namespace std;

int main() {
	long long int answer = 1;

	for(int i=3; i<=1001; i+=2)
		answer += ( 4*((i*i)-(((i-1)/2)-1+i)) );

	cout << answer << endl;
	return 0;
}

exploit the fact that the spirals expand predictably.

Good answer. It becomes much simpler if you map out the monad in simple terms, where the sum =

markupf(n) = 4(2n+1)2 – 12n + f(n-1)


thehare's Avatar
Member
0 0

Haha after reading these replies, I realize just how much my inexperience is showing :xx: LOL


ShadowGate's Avatar
Member
0 0

stranac wrote: You can use a step argument in range like this:

for i in range(3, 1002, 2):

Awesome I learned something about the range() function that I didn't know before. Thanks stranac. And fixed it looks much better and more pythonic.

Smaller source, faster execution. time: 0.01s memory: 4676 kB

for i in range(3, 1002, 2):
    answer += (4*((i*i)-(((i-1)/2)-1+i)))
print(answer)```