8
\$\begingroup\$

Given a linear equation mx+n, return n and m. However, the equation may be in any of the following formats:

5x+2 -> 5 2
5x-2 -> 5 -2
5x   -> 5 0
-2   -> 0 -2
x    -> 1 0

Here are the formats, where each ? stands for a positive integer written without leading zeroes

?x+?
?x-?
-?x+?
-?x-?
x+?
x-?
?
-?
?x
-?x
x

All of these cases must be handled.

Specifications:

  • You can assume that the equation is in one of the above formats, i.e. it matches the regex ^(-?[123456789]\d*)?x([+-][123456789]\d*)?|-?[123456789]\d*$.

Test Cases:

-2x+3 -> -2 3
44x   -> 44 0
-123  -> 0 -123
x     -> 1 0
-1x   -> -1 0
\$\endgroup\$
10
  • 1
    \$\begingroup\$ What about output formats? Would e.g. 1 +2 be a valid output for 1x+2? \$\endgroup\$ Commented May 12, 2017 at 19:24
  • \$\begingroup\$ Adding on to what @PeterTaylor said, the python answer adds an L to the end of numbers if they get too big. Should this be allowed? \$\endgroup\$
    – Okx
    Commented May 12, 2017 at 19:30
  • \$\begingroup\$ @PeterTaylor You can use any valid output format. \$\endgroup\$ Commented May 12, 2017 at 19:49
  • \$\begingroup\$ Is it valid to output constants as length-1 lists, and true linear polynomials as length-2 lists? So for example, 7x is output as 7 0 but 7 is output as just 7? \$\endgroup\$ Commented May 12, 2017 at 20:06
  • \$\begingroup\$ @GregMartin No, you must always output both numbers. \$\endgroup\$ Commented May 12, 2017 at 20:07

13 Answers 13

12
\$\begingroup\$

Python 2, 55 bytes

j=1j
c=eval(input().replace(*'xj'))
print c.imag,c.real

Try it online!

Uses Python's built-in code evaluation. The input is formatted like a complex number by replacing x withj, Python's complex unit. Because only literals like 2j are recognized, but not j or -j, the variable j is assigned as 1j to cover those.

Unfortunately, Python doesn't seem to have a built-in to convert a complex number to a pair of reals.

\$\endgroup\$
1
  • 1
    \$\begingroup\$ Oh nice thinking :D \$\endgroup\$ Commented May 12, 2017 at 19:50
4
\$\begingroup\$

Mathematica, 16 bytes

Inspired by xnor's Python 2 answer:

ReIm[I#/.x->-I]&

Takes input as a literal expression (not a string), and returns a pair of numbers. It works by making x a complex number then taking the real and imaginary parts — the only non-obvious bit is multiplying by i to start with, to get the output in the right order.

We can also use

ReIm[x=-I;I#]&

for 14 bytes (tied with Jelly!), but setting x to equal -i before taking the input, instead of just replacing x afterwards, feels like cheating…

\$\endgroup\$
3
  • 1
    \$\begingroup\$ Nice solution. I never new it had a ReIm function, I've always been doing {Re[#],Im[#]}&. You've helped a lot there. \$\endgroup\$
    – Ian Miller
    Commented May 13, 2017 at 7:33
  • \$\begingroup\$ @IanMiller, ReIm was only introduced in version 10.1, so it's possible your copy of Mathematica doesn't have it. \$\endgroup\$
    – Not a tree
    Commented May 13, 2017 at 7:36
  • 2
    \$\begingroup\$ Ah. I do have 10.1 but I have been using old versions for far longer. They add way too many functions each update. :). \$\endgroup\$
    – Ian Miller
    Commented May 13, 2017 at 7:39
3
\$\begingroup\$

JavaScript (ES6), 53 48 bytes

s=>([a,b]=s.split(/x\+?/),1/b?[a||1,b||0]:[0,s])

Test cases

let f =

s=>([a,b]=s.split(/x\+?/),1/b?[a||1,b||0]:[0,s])

console.log(f("-2x+3")) // -> -2 3
console.log(f("44x"))   // -> 44 0
console.log(f("-123"))  // -> 0 -123
console.log(f("x"))     // -> 1 0
console.log(f("-1x"))   // -> -1 0

\$\endgroup\$
3
  • \$\begingroup\$ works not for -x try my regex \$\endgroup\$ Commented May 12, 2017 at 22:08
  • \$\begingroup\$ @JörgHülsermann If I understand the rules correctly, -x is not a valid input. \$\endgroup\$
    – Arnauld
    Commented May 12, 2017 at 22:10
  • \$\begingroup\$ You are right sorry \$\endgroup\$ Commented May 12, 2017 at 22:12
3
\$\begingroup\$

sed, 44 42 bytes

s:+::
s:x: :
t
s:^:0 :
:
s:^ :1 :
s: $: 0:

Try it online!

I/O: one per line.

-2 bytes thanks to @KritixiLithos.

\$\endgroup\$
3
  • \$\begingroup\$ You can do t and : instead of using the a label \$\endgroup\$
    – user41805
    Commented May 13, 2017 at 6:43
  • \$\begingroup\$ @KritixiLithos Seems to work somehow, thanks! \$\endgroup\$
    – eush77
    Commented May 13, 2017 at 9:03
  • \$\begingroup\$ The first two substitutions can be combined into one. \$\endgroup\$
    – user41805
    Commented Nov 22, 2019 at 7:04
2
\$\begingroup\$

Jelly, 18 14 bytes

”x;ṣ”xVṫ-µ¬ṂW+

Test suite at Try it online!

How?

”x;ṣ”xVṫ-µ¬ṂW+ - Main link: list of characters s  examples: "5x-2"         "x"       "-123"
”x             - literal 'x'
  ;            - concatenate with s                        "x5x-2"        "xx"      "x-123"
   ṣ”x         - split on 'x's                        ["","5","-2]  ["","",""]  ["","-123"]
      V        - evaluate as Jelly code (vectorises)      [0,5,-2]     [0,0,0]     [0,-123]
       ṫ-      - tail from index -1 inclusive               [5,-2]       [0,0]     [0,-123]
         µ     - monadic chain separation (call that z)
          ¬    - not z                                       [0,0]       [1,1]        [1,0]
           Ṃ   - minimum                                         0           1            0
            W  - wrap in a list                                [0]         [1]          [0]
             + - add to z (vectorises)                      [5,-2]       [1,0]     [0,-123]
\$\endgroup\$
2
\$\begingroup\$

PHP, 73 Bytes

preg_match("#((.*)x)?\+?(.*)#",$argn,$t);echo$t[1]?$t[2]?:1:0," ",+$t[3];

Try it online!

PHP, 91 Bytes

works also with -x

preg_match("#((-)?(\d+)?x)?\+?(-?\d+)?#",$argn,$t);echo$t[2],$t[1]?$t[3]?:1:0," ",$t[4]?:0;

Try it online!

\$\endgroup\$
2
\$\begingroup\$

Mathematica, 23 bytes

Coefficient[#,x,{1,0}]&

Try it online

copy and paste with ctrl-v this code

Coefficient[#,x,{1,0}]&[-2x+3]

and press shift+enter to run

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

Python 2, 71 bytes

lambda s:([0,]+[int(x or`1-i`)for i,x in enumerate(s.split('x'))])[-2:]

Try it online!

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

Mathematica, 33 bytes

#~CoefficientList~x/.{a_}:>{a,0}&

Pure function taking an expression in the expected format (note: not a string, but a pure expression like -2x+3), and returning an ordered pair of integers with the constant coefficient appearing first (for example, -2x+3 returns {3,-2}).

The builtin CoefficientList (which works for polynomials of any degree) does the heavy lifting; its default behavior is to return constants as length-1 lists, so /.{a_}:>{a,0} overrides that and makes the 0 coefficient of x appear explicitly.

\$\endgroup\$
1
  • \$\begingroup\$ I was wondering how long it would be until a Mathematica answer was posted. \$\endgroup\$ Commented May 12, 2017 at 20:19
0
\$\begingroup\$

Retina, 38 bytes

x$
x+0
^[^+-]*$
0x+$+
^[^-\d]
1$+
-
+-

Definitely can be improved.

Possibly stretching how we are allowed to format output. It just outputs a complete equation, as in n and m separated by x+

Try it online!

\$\endgroup\$
3
  • \$\begingroup\$ This fails for an input like x-1 \$\endgroup\$
    – Leo
    Commented May 12, 2017 at 19:34
  • \$\begingroup\$ @Leo Thanks, fixed. \$\endgroup\$
    – Okx
    Commented May 12, 2017 at 19:36
  • \$\begingroup\$ I'm fairly confident you can replace [^+-]* with \w* \$\endgroup\$
    – user41805
    Commented May 12, 2017 at 20:17
0
\$\begingroup\$

Octave, 45 bytes

@(a)[imag(u=eval(strrep(a,'x','j'))),real(u)]

Try it online!

Evaluate the expression, with x replaced by complex j. Octave is very flexible when it comes to complex expressions, with j,1j,i and 1i all equivalent (with the advantage that 1j and 1i cannot be overwritten by variables, but that's irrelevant for this challenge). Inline expression is used to build a list of [imag(u) real(u)] with u the complex number.

I initially wanted to try a more idiomatic approach, using the built-in sym2poly. For example (already at 47 bytes to make sure 0*x is handled):

@(a)sym2poly([strrep(a,'x','*x') '+x^2']))(2:3)

This one however failed on the case of x without coefficient. In the end a real/complex setup like xnor turned out to be optimal.

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

MATL, 12 bytes

120'i'ZtU&Zj

Try it online!

Port of my Octave answer, but of course adapted for compactness in MATL. Explanation:

120'i'Zt     % Replace character 120 ('x') by 'i' in input (implicit).
             % (Used 120 instead of 'x' to save a separator between 'x' and 'i')
        U    % Convert string to complex number
         &Zj % Split complex number in real and imaginary part. Implicit display.
\$\endgroup\$
0
\$\begingroup\$

C (gcc),145 138 112 bytes

f(char*s){int a,b,i=0;sscanf(s,"%dx%d",&a,&b);if(L!=0)i=(int)(L-s);printf("%d %d",s[i]=='x'?a:0,s[i]=='x'?b:a);}

Try it online!

void f(char*s)
{
    int a,b,i=0;
    sscanf(s,"%dx%d",&a,&b);

    if(L!=0)
      i=(int)(L-s);

    printf("%d %d",s[i]=='x'?a:0,s[i]=='x'?b:a);
}

Can definitely be shortened, but dont see it now!

\$\endgroup\$
3
  • \$\begingroup\$ 1. You don't need the space in char *s 2. Can't you remove whitespace? \$\endgroup\$ Commented May 15, 2017 at 0:52
  • \$\begingroup\$ @Challenger5 Thanks! I used a random online byte counter website yesterday, tried it now on TIO, code is a lot shorter, thanks for pointing out! :) \$\endgroup\$
    – Abel Tom
    Commented May 15, 2017 at 11:49
  • \$\begingroup\$ Suggest printf("%d %d",s[i]-'x'?:a,s[i=L?L-s:i]-'x'?a:b); instead of if(L!=0)i=(int)(L-s);printf("%d %d",s[i]=='x'?a:0,s[i]=='x'?b:a); and index() instead of strchr() \$\endgroup\$
    – ceilingcat
    Commented Nov 7, 2018 at 0:07

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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