8
\$\begingroup\$

Note: as this question has been marked as a duplicate, I have accepted an answer. However, I will still check this question if users can find a shorter way of doing it, and accept that answer.

Given two numbers (which are multiples of 0.5) representing heads-percentage and tails-percentage from a series of coin-flipping, output the minimum amounts of heads and tails to produce percentages such as those. Input and output can be in any form. However, output must be in a readable format (Good examples are x y, [x y], etc).

Examples:

  • Input: 25 75 (25% heads, 75% tails) Output: 1 3 (an output of 25 75 is invalid since that is not the minimum amounts of heads and tails to produce those percentages)
  • Input: 30 70 (30% heads, 70% tails) Output: 3 7
  • Input: 99.5 0.5 (99.5% heads, 0.5% tails) Output: 199 1

You may assume that there will always be a digit before and after a decimal point in an input (no .5s or 15.s). You may also assume the input adds up to 100%. This is , shortest code in bytes wins!

\$\endgroup\$
13
  • \$\begingroup\$ Can the numbers be taken as a list? As two number inputs? \$\endgroup\$
    – xnor
    Commented Oct 29, 2015 at 4:23
  • \$\begingroup\$ @xnor either is fine \$\endgroup\$
    – GamrCorps
    Commented Oct 29, 2015 at 4:23
  • \$\begingroup\$ Would [199.0, 1.0] a valid output for the last example? \$\endgroup\$
    – Dennis
    Commented Oct 29, 2015 at 4:29
  • 8
    \$\begingroup\$ This might effectively be the same as simplifying a fraction. My answer there is basically the same as here except for input processing. \$\endgroup\$
    – xnor
    Commented Oct 29, 2015 at 5:02
  • 1
    \$\begingroup\$ Also similar to this one. \$\endgroup\$
    – grc
    Commented Oct 29, 2015 at 8:57

9 Answers 9

12
\$\begingroup\$

Dyalog APL, 3 bytes

,÷∨

This is a dyadic function train that accepts the percentages as left and right arguments:

┌─┼─┐
, ÷ ∨

It is equivalent to the following, train-less function:

{(⍺,⍵)÷⍺∨⍵}

Try it online on TryAPL.

How it works

  ∨  Compute the GCD of both arguments.
,    Concatenate both arguments.
 ÷   Divide the latter by the former.
\$\endgroup\$
2
  • 2
    \$\begingroup\$ There is literally no way this can be beaten. Excellent job! :D \$\endgroup\$
    – Alex A.
    Commented Oct 29, 2015 at 5:45
  • 4
    \$\begingroup\$ I really should learn this language, it looks fascinating. \$\endgroup\$
    – user4768
    Commented Oct 29, 2015 at 7:50
7
\$\begingroup\$

Python 2, 47 bytes

A,B=a,b=input()
while b:a,b=b,a%b
print A/a,B/a

Takes input like 15,20 and prints the output like 3 4.

Performs the Euclidian algorithm to find the gcd, then scales the numbers by it.

Fortunately, Python will happily compute % on fractions, so inputs like 0.5 99.5 behave just the same. More type-strict languages (cough, Haskell) aren't so lucky.

\$\endgroup\$
1
  • \$\begingroup\$ Also, floats are annoying in Haskell. 20/100*5 is not equal to 20/100 + 20/100 + 20/100 + 20/100 + 20/100, which is what is put in lists like [0,20/100..] \$\endgroup\$ Commented Nov 3, 2015 at 11:00
7
\$\begingroup\$

J, 4 bytes

,%+.

Explanation:

       (x +. y)     NB. GCD of the left and right inputs
      %             NB. divided by
(x, y)              NB. a vector consisting of the inputs

Try it online

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

CJam, 25 14 bytes

{_~{_@\%}h;f/}

This is an unnamed function that pops a list from the stack and leaves one in return. Like @xnor's answer, it uses the Euclidean algorithm to find the GCD, then divides the list elements by it.

Try it online in the CJam interpreter.

How it works

_             Push a copy of the input array.
 ~            Dump its elements on the stack.
  {    }h     Do:
   _            Push a copy of the topmost integer.
    @           Rotate the bottom-most integer on top of it.
     \          Swap them.
      %         Calculate the residue of their division.
              While the residue is positive, repeat the loop.
         ;    Discard the last residue (0).
              This leaves the GCD on the stack.
          f/  Divide the elements of the input array by their GCD.
\$\endgroup\$
3
\$\begingroup\$

Pyth, 12 bytes

J/R.5Q/RiFJJ

Like @xnor's answer, this divides each list item by their GCD. Pyth has the GCD as a built-in, but it doesn't work for floats out of the box.

Try it online.

How it works

              (implicit) Save the evaluated input in Q.
 /R.5Q        Divide each element of Q by 0.5.
              This transforms the array's floats into integers.
J             Save the result in J.
        iFJ   Compute the GCD of the elements of J.
      /R   J  Divide the elements of J by their GCD.
\$\endgroup\$
3
  • \$\begingroup\$ Since the numbers are multiples of 0.5, could you multiply the inputs by 2, and then use the integer GCD? \$\endgroup\$ Commented Oct 29, 2015 at 5:50
  • \$\begingroup\$ That's actually what I'm doing. /R.5 divides by 0.5, casting to integer in the process. \$\endgroup\$
    – Dennis
    Commented Oct 29, 2015 at 5:51
  • \$\begingroup\$ Oh, ok, that makes sense. From the description I got the impression that you might not be using the built-in GCD, and went for the Euclid algorithm instead. \$\endgroup\$ Commented Oct 29, 2015 at 6:04
1
\$\begingroup\$

APL, 20 bytes

{⍺⍵÷⍺{0<⍵:⍵∇⍵|⍺⋄⍺}⍵}

This creates an unnamed dyadic function that accepts the inputs on the left and right and returns an array. Unlike Dennis' super slick Dyalog solution, this works with other versions of APL because it doesn't use trains and it doesn't assume that GCD () works for floats.

Explanation:

    ⍺{0<⍵:⍵∇⍵|⍺⋄⍺}⍵}   ⍝ Compute the GCD of the inputs using the Euclidean algorithm
{⍺⍵÷                   ⍝ Divide the inputs by their GCD

Try all test cases online

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

Mathematica, 21 bytes

#/GCD@@Rationalize@#&

Another program with the same byte count is

#/GCD@@(Floor[2#]/2)&

Mma has never supported FP well...

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

TI-BASIC, 31 22 24 bytes

Forgot to count new lines before...

Prompt A,B  
gcd(2A,2B➡C 
Disp 2A/C,2B/C 

This was done in the middle of math class...

\$\endgroup\$
5
  • \$\begingroup\$ You can skip the closing parenthesis in the third line. \$\endgroup\$
    – Ypnypn
    Commented Oct 29, 2015 at 13:20
  • \$\begingroup\$ And you can use Disp instead of Output to save about 8 bytes. \$\endgroup\$
    – Ypnypn
    Commented Oct 29, 2015 at 13:21
  • \$\begingroup\$ Also, chainging the top two lines to 'Prompt A,B' might help. \$\endgroup\$
    – GamrCorps
    Commented Oct 29, 2015 at 13:22
  • \$\begingroup\$ You can use the implicit Disp at the end if you output as a list: 2/C{A,B. \$\endgroup\$
    – lirtosiast
    Commented Oct 29, 2015 at 17:34
  • \$\begingroup\$ If you also take input as a list from Ans there's an 11 byte solution: 2Ans/min(gcd(2Ans,min(2Ans \$\endgroup\$
    – lirtosiast
    Commented Oct 29, 2015 at 18:04
0
\$\begingroup\$

Common Lisp, 168 94

(let((x(floor(*(read)2)))(y(floor(*(read)2))))(format t "~A ~A"(/ x(gcd x y))(/ y(gcd y x))))

I missed the original bit about everything being a multiple of 0.5 (thanks xnor!), so this is a good bit shorter than my first go (Gotta' love that almost a third of those bytes are parentheses.)

\$\endgroup\$
2
  • \$\begingroup\$ You're guaranteed the inputs are multiples of 0.5, so doubling suffices to make them whole. \$\endgroup\$
    – xnor
    Commented Oct 29, 2015 at 8:00
  • \$\begingroup\$ Oh wow, I didn't even notice that. I'll shorten this answer right quick, thanks. \$\endgroup\$
    – Candles
    Commented Oct 29, 2015 at 8:01

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