7
\$\begingroup\$

Your task is to implement a floor function in as few bytes as possible.

A floor function is a function that takes a real number and returns the largest integer less than or equal to the input.

Your program should support both positive and negative inputs. Since it is provably impossible to support all real numbers you need only support a reasonable subset of them. This subset should include positive numbers, negative numbers and of course numbers that are not integers. Such number systems include fixed-point numbers, floating point numbers and strings.

Your code may be a complete program or function.

This is so answers will be scored in bytes with less bytes being a better score.

\$\endgroup\$
  • 1
    \$\begingroup\$ Any limits on the size of the numbers to be handled correctly? Need to treat negatives? \$\endgroup\$ – dmckee Jan 31 '11 at 17:00
  • 1
    \$\begingroup\$ I ask about range because single precision IEEE 745 floating point runs up to 2^127, which is to say that 64 bit integers would not be sufficient. \$\endgroup\$ – dmckee Jan 31 '11 at 17:21
  • \$\begingroup\$ @dmckee The problem definition states any real number, not just positive ones. As far as number size is concerned, let's assume that is not a concern (i.e., an answer that handles that case is not necessarily better than an answer that doesn't handle that case, unless of course it is of equal or lesser length). \$\endgroup\$ – Daniel Standage Jan 31 '11 at 19:39
  • 2
    \$\begingroup\$ In golfscript, this would be zero bytes since x is already an integer :) \$\endgroup\$ – gnibbler Jan 31 '11 at 20:53
  • 1
    \$\begingroup\$ @TheGuywithTheHat Type casting is fine, but this does not give the correct answer. \$\endgroup\$ – Daniel Standage Apr 7 '14 at 17:15

26 Answers 26

4
\$\begingroup\$

PARI/GP (10)

In gp (and some other languages) x%1 gives the decimal part of x:

f(x)=x-x%1

NOTE: For negative x, x%1 returns (1 - abs(decimal part of x)), so the above works both for positive and negative numbers.

\$\endgroup\$
  • 1
    \$\begingroup\$ @Joey: no it does not. Yields -4 for floor(-3.1234); -4 for floor(-4). What do you get? \$\endgroup\$ – Eelvex Jan 31 '11 at 17:10
  • \$\begingroup\$ x - x % 1 gives -3 for -3.1234, surely, when the expected answer is -4 \$\endgroup\$ – Nellius Jan 31 '11 at 17:30
  • \$\begingroup\$ @Nellius: NO, because -3.1234%1 = 0.8766. \$\endgroup\$ – Eelvex Jan 31 '11 at 17:39
  • 1
    \$\begingroup\$ Ok, I take that back, partially. Because the sign of the modulus result depends on the operand in some languages but not in others. For me, -3.14 % 1 yields -.14 (PowerShell). Now, if you'd be so kind to make a null edit so I can take the downvote back? :-) \$\endgroup\$ – Joey Jan 31 '11 at 17:40
  • 1
    \$\begingroup\$ You can shave off 2 characters with x->x-x%1. If not for the restriction you could use x->x\1 which is another 2 characters shorter. \$\endgroup\$ – Charles Apr 28 '15 at 14:48
4
\$\begingroup\$

DC (15 bytes)

Makes use of a nifty little trick that occurs during division in DC. Add a 'p' to then end to get output (it performs the floor correctly anyway), I assume that stuff is not already on the stack, and that input is in stdin.

[1-]sazk?z/d0>a

EG: echo 0 2.6 - | dc -e '[1-]sazk?z/d0>ap'

\$\endgroup\$
4
\$\begingroup\$

Python (81)

def f(x):return str(x - float("." + str(float(x)).split('.')[-1])).split('.')[0]
\$\endgroup\$
  • \$\begingroup\$ You can go down to 76 bytes by removing unnecessary spaces! def f(x):return str(x-float("."+str(float(x)).split('.')[-1])).split('.')[0] \$\endgroup\$ – Daniel Dec 26 '15 at 5:03
4
\$\begingroup\$

JavaScript, 50 34 33 32 characters

function f(n){return~~n-(~~n>n)}

Works the same way as the PHP one I submitted.

\$\endgroup\$
  • 1
    \$\begingroup\$ 32 chars if you drop the ; \$\endgroup\$ – zzzzBov Mar 12 '11 at 6:04
  • 2
    \$\begingroup\$ If you use ES6, it is 14 characters:n=>~~n-(~~n>n) \$\endgroup\$ – Generic User Dec 26 '15 at 14:07
3
\$\begingroup\$

C (51)

int F(float x){int i=x-2;while(++i<=x-1);return i;}
\$\endgroup\$
  • \$\begingroup\$ Generally code gold answers are expected to be in the form of either a function or a complete program (here the OP has selected a function), so you need the int f(float c){} bit. \$\endgroup\$ – dmckee Jan 31 '11 at 17:32
  • \$\begingroup\$ @dmckee: forgot that, sorry. \$\endgroup\$ – Eelvex Jan 31 '11 at 17:44
  • \$\begingroup\$ Why <=x-1? would <x not be exactly the same thing, but 3 characters shorter? \$\endgroup\$ – Nellius Jan 31 '11 at 20:11
  • \$\begingroup\$ @Nellius: no, it's not the same (unfortunately). \$\endgroup\$ – Eelvex Jan 31 '11 at 20:21
  • \$\begingroup\$ @Nellius: only when x is an integer: compare "<=3.5-1" with "<3.5". \$\endgroup\$ – R. Martinho Fernandes Feb 2 '11 at 1:50
3
\$\begingroup\$

LISP (26)

(Same trick as in PARI/GP answer)

(defun f(x)(- x(mod x 1)))
\$\endgroup\$
  • \$\begingroup\$ You can strip off the space before the (mod. \$\endgroup\$ – Chris Jester-Young Jan 31 '11 at 20:06
  • \$\begingroup\$ @Chris: :) Thx. \$\endgroup\$ – Eelvex Jan 31 '11 at 20:12
3
\$\begingroup\$

C 126 (including NL)

Doesn't use any built-in conversion such as (int)x.

r(float x) {
int
p=*(int*)&x,
f=p&8388607|1<<23,
e=((p>>23)&255)-150;
if(e>0)f*=1<<e;
if(e<0)f/=1<<-e;
return p>>31?-f-1:f;
}
\$\endgroup\$
3
\$\begingroup\$

Python (20)

f=lambda x:int(x//1)

or, if the result doesn't need to be of type int, 15 characters:

f=lambda x:x//1
\$\endgroup\$
3
\$\begingroup\$

J 7 chars

f=:-1&|  NB. x - (x mod 1)

eg.

f 3.14
3
f _3.14
_4
\$\endgroup\$
  • 1
    \$\begingroup\$ Is there a good reason this isn't the accepted answer? \$\endgroup\$ – cat Dec 26 '15 at 20:02
2
\$\begingroup\$

Ruby 1.9 (12 14)

 f=->x{x-x%1}

It's more a "for the record" type solution along the lines of the PARI/GP one.

>> f[3.4] #=> 3.0
>> f[-3.4] #=> -4.0
\$\endgroup\$
  • \$\begingroup\$ You don't need the parentheses around x%1. \$\endgroup\$ – Ventero Mar 14 '11 at 19:22
2
\$\begingroup\$

C (80)

Well it's not the shortest, but it's a great opportunity to show off my bit twiddling skills :D.

main(){int I,X=0x7FFFFF;scanf("%f",&I);printf("%d",((I&X)|X+1)>>-(I>>23)+150);}
\$\endgroup\$
1
\$\begingroup\$

Perl (23)

$_=int($_)-(int($_)>$_)

Example:

perl -ple '$_=int($_)-(int($_)>$_)'

Every value entered on input will now be printed "floored".

Its bass5098's technique, but smaller =).

As a function(36):

sub f{int($_[0])-(int($_[0])>$_[0])}
\$\endgroup\$
  • \$\begingroup\$ Any particular reason for shying away from regex? \$\endgroup\$ – Codefun64 Dec 27 '15 at 7:07
1
\$\begingroup\$

C# (56 chars):

My quick and naive answer earlier had a stupid logical flaw in it. Two approaches here, which I believe are both the same length. Double approach relies on the fact that casting to int removes the decimal part of a double.

int F(double d){return(int)(d%1==0?d:(int)d-(d<0?1:0));}

Decimal approach relies on the fact that d%1 returns the decimal part of the number for decimal data type.

int F(decimal d){return(int)(d%1==0?d:d-d%1-(d<0?1:0));}

Could save a few characters in both cases by returning their own type instead of int, but I feel a floor function should return an int.

\$\endgroup\$
  • \$\begingroup\$ You can use float instead and save a byte. \$\endgroup\$ – Joey Mar 12 '11 at 10:52
1
\$\begingroup\$

PHP, 51 45 43 37 characters

function f($n){return~~$n-(~~$n>$n);}

This should be able to be applied to most languages that do not support the n%1 trick.

\$\endgroup\$
  • \$\begingroup\$ Since this does not need to be an independently working program, I think you can safely trim the first 3 characters (i.e. the <? ) off your solution. \$\endgroup\$ – Daniel Standage Jan 31 '11 at 21:55
1
\$\begingroup\$

APL, 5 bytes

x-1|x

x is the input. Writes the output to screen.

\$\endgroup\$
1
\$\begingroup\$

RProgN 2, 4 bytes

]1%-

Explained

]1%-
]   # Duplicate the implicit input
 1% # Modulo 1
   -# Subtract Modulo 1 of the input from the input, inplicitly outputting the floor'd result.

Try it online!

\$\endgroup\$
0
\$\begingroup\$

Python, 13

If the OP wants all functions to be non-anonymous, add f= to the front of each for two additional characters.

lambda x:x//1

Since x%1 returns the amount following the decimal point, this is pretty short (14):

lambda x:x-x%1

If using cast to integer instead, it's one character longer (15):

lambda x:int(x)

The shortest using string casting I could come up with (40):

lambda x:int(`x`.split('.')[0])+cmp(x,0)
\$\endgroup\$
0
\$\begingroup\$

MATL, 5 bytes

The programming language used in this answer was created after the challenge was posted.

it1\-

Examples

>> matl it1\-
> 5.6
5

>> matl it1\-
> -5.2
-6

Explanation

Pretty straightforward. It uses a modulo operation with divisor 1.

i      % input                                                              
t      % duplicate                                                          
1      % number literal                                                     
\      % modulus after division
-      % subtraction
\$\endgroup\$
  • \$\begingroup\$ You should note that this language was developed wayyyyyy after this challenge. \$\endgroup\$ – cat Dec 26 '15 at 17:58
  • 1
    \$\begingroup\$ @cat Sorry, I hadn't noticed. Disclaimer added \$\endgroup\$ – Luis Mendo Dec 26 '15 at 18:00
0
\$\begingroup\$

Mouse-2002, 13 bytes

Second place, ahh! (And this is a full program, not a function definition)

?&DUP &FRAC -

Take the fractional bit of the input and subtract it from the input.

\$\endgroup\$
0
\$\begingroup\$

Perl 5, 22 bytes

s/\..+//&&$_<0?$_--:$_

This is larger than my first answer, which merely truncated the number - so, for negative numbers, it wasn't correct. This was due to a misunderstanding on my part of what a floor function does.

\$\endgroup\$
0
\$\begingroup\$

ES8, 22 bytes

f=n=>return~~n-(~~n>n)

\$\endgroup\$
  • \$\begingroup\$ Welcome to PPCG! You can remove the f= part as anonymous functions are allowed. \$\endgroup\$ – Erik the Outgolfer Sep 3 '17 at 18:43
0
\$\begingroup\$

Java 8, 19 bytes

Lambda from double to int. There are plenty of choices for types to assign to: Function<Double, Integer>, DoubleFunction<Integer>, or DoubleToIntFunction.

n->(int)(n<0?n-1:n)

Try It Online

\$\endgroup\$
0
\$\begingroup\$

x86_64 machine language (Linux), 11 bytes

0:       c4 e3 79 0b c0 01       vroundsd $0x1,%xmm0,%xmm0,%xmm0
6:       f2 0f 2c c0             cvttsd2si %xmm0,%eax
a:       c3                      retq

This requires a processor with AVX instructions.

To Try it online!, compile and run the following C program.

#include<stdio.h>
#include<math.h>
int f(double x){return floor(x);}
const char g[]="\xc4\xe3\x79\x0b\xc0\x01\xf2\x0f\x2c\xc0\xc3";

int main(){
  for( double d = -1.5; d < 1.5; d+=.2 ) {
    printf( "%f %d %d\n", d, f(d), ((int(*)(double))g)(d) );
  }
}

\$\endgroup\$
0
\$\begingroup\$

RProgN, 1 byte

_

A builtin, thanks to the new challenge spec.

Try it online!

\$\endgroup\$
0
\$\begingroup\$

AArch64 machine language (Linux), 8 bytes

0: 1e700000 fcvtms w0, d0
4: d65f03c0 ret

To try it out, compile and run the following C program

#include<stdio.h>
#include<math.h>
int f(double x){return floor(x);}
const char g[]="\x00\x00\x70\x1e\xc0\x03\x5f\xd6";

int main(){
  for( double d = -1.5; d < 1.5; d+=.2 ) {
    printf( "%f %d %d\n", d, f(d), ((int(*)(double))g)(d) );
  }
}
\$\endgroup\$
-1
\$\begingroup\$

TI-Basic, 4 bytes

X-fPart(X

fPart( is a one-byte token, stands for 'fractional part' and returns anything right of the decimal point. Parentheses don't need to be closed in TI-Basic.

\$\endgroup\$
  • 1
    \$\begingroup\$ Doesn't work for negative numbers. \$\endgroup\$ – lirtosiast Oct 10 '15 at 22:21

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.