Algorithms!

Posted by ludamad on Dec. 11, 2008, 8:32 p.m.

Alright 64Digits, show me your stuff. I will describe three programming situations, and you will describe, or write, the most efficient algorithm for each situation. Most efficient answer wins. Anything goes, but no punches below the belt.

You can give me your answer in words, or give it to me in any language if you feel that is easier.

All questions have been devised by me, although they aren't that original.

Situation 1:

You are given a positive integer and must find out if it can be created by the factorial of a positive, integer number.

Details:

A factorial of a positive integer number is the number multiplied by all integers below it.

Situation 2:

You are given a million integers in the range 0 to 100. You must output them numerically sorted, least to greatest.

Details: Assume the integers are coming from some input function, and you are printing your result in some output function.

Situation 3:

You are given the 2D dimensions of a box, and then the dimensions of a smaller box. Taking into account 90 degree rotations (that is, exchanging the width and height of the smaller box), what is the largest amount of smaller boxes that can fit in the area of the bigger box?

Details:

Your algorithm should waste as little space as possible. No two smaller boxes are allowed to touch. No smaller box is allowed to go out of the bounds of the bigger box.

Do any of the situations you please, I will announce winners by situation next blog.

Comments

Theonlywonderboy 15 years, 11 months ago

I respond with a resounding "What?". Man do I feel stupid. Oh well I lost that one…and the game.

Cesar 15 years, 11 months ago

What do you mean "taking into account 90 degree rotations"?

ludamad 15 years, 11 months ago

Added clarification about the rotation

SteveKB 15 years, 11 months ago

fn=1

fns=1

fint=36

limit=100

fail=0

while!(fint=fn)and(fail=0){

fns++

fn*=fns

if(fns=limit)or(fint<fn){fail=1}

}

That is for the first one. :p

EDIT: yeah after going to do something else I came back and realized that :p if you don't care about limits and the integer is a reasonable number then you can get rid of the limit stuff and leave it as

fn=1 //reset factorial number

fns=1 //reset factorial number sequence

fint=8139 //random positive integer number (round(random(9000)))

fail=0 //reset fail

while!(fint=fn)and(fail=0){ //checks if hasn't failed and whether factorial number matches the random integer number

fns++ //goes to next factorial number sequence (adds 1)

fn*=fns //multiplies by next factorial number sequence

if(fint<fn){fail=1} //checks if factorial number has already passed random positive integer number

}

here is a clean version

fn=1 fns=1 fint=(positive integer) fail=0

while!(fint=fn)and(fail=0){

fns++ fn*=fns

if(fint<fn){fail=1}}

ludamad 15 years, 11 months ago

Meow: Your thing could run forever :P

ludamad 15 years, 11 months ago

Yeah, your code is a bit hard to follow but I can at least see you understand the proper solution.

SteveKB 15 years, 11 months ago

for the second one assuming you can store that many variables.

mydsl=ds_list_create()

repeat(1000000){

ds_list_add(mydsl,inputfunction)}

ds_list_sort(mydsl,1)

seq=0

repeat(1000000){

draw_text(0,seq*16,ds_list_find_value(mydsl,seq))

seq++

}

maybe input function is something like round(random(100))

here is the meaning

mydsl=ds_list_create() //creates ds_list for storing list of numbers

repeat(1000000){ //repeats for 1million variables

ds_list_add(mydsl,inputfunction)} //adds a variable to the list using the inputfunction as the number

ds_list_sort(mydsl,1) //sorts the list in ascending order

seq=0 //sets list sequence number

repeat(1000000){ //repeats million times for million numbers

draw_text(0,seq*16,ds_list_find_value(mydsl,seq))//draws numbers 16 pixels from each of their origions with the variable recieved for the sequence.

seq++ //adds one to sequence

}

clean version

mydsl=ds_list_create()

repeat(1000000){ds_list_add(mydsl,round(random(100)))}

ds_list_sort(mydsl,1) seq=0

repeat(1000000){

draw_text(0,seq*16,ds_list_find_value(mydsl,seq)) seq++}

EDIT: going to bed and haven't tried number 3 yet :p

ludamad 15 years, 11 months ago

For the record, ds_list_sort has really bad performance for 1 million items. Sk8 has given me a better answer for #2. Number 3 very well may be NP (google it).

SteveKB 15 years, 11 months ago

can I see sk8's answer later *zzzz*

Kenon 15 years, 11 months ago

My version of #1:

Quote: Code Snippet Idea

num=X//This is the number

i=2

while(num>1)

{num/=i;

i+=1;}

return (num==1);

APPARENTLY DIVISION SUCKS BALLS, so my theory does not work out to be faster, but it does look better.

My idea on #3 comes from partitioning.

Too lazy to code it, but yeah.

Quote: Code idea

Dimensions of Large Box stored in 2 vars.

Dimensions of small box stored in 2 vars.

Storage variable for the number of boxes

While the box's variables are each larger than the small one's,:

{Check for larger box var, subtract largest small from it.

Add to the storage variable: smaller var of big box/smaller var of small box.}

return boxes

I think it works, I SERIOUSLY doubt it's the most efficient way, but I'm gonna probably do a code for it later.

In case no one understands the last one:

My idea is like that. We start off with the boxes. We then partition on the longest side a box area going down which we cram with boxes. We then cut it away and remember the number. We repeat that on the next cutting away, The third one, we rotate so that the long ways is horizontal. Fill it up and down to the brim. CUT. We reswitch for the last one, do some cutting (I was too lazy to show my method switches back, cuts the 7x5 with 2 small boxes and leaves a 3x5 with one left, then we cut away a 2x4 out of that), then add up the rest.