18
\$\begingroup\$

Create a function which takes a polynomial equation, a value for x and returns the result of the operation.

Example: given 4x^2+2x-5 and x=3 output 37. This is the result of 4(3)^2+2(3)-5

  • Assume all polynomials are valid
  • Polynomial format will always be coefficient(variable)^exponent => 4x^2 except :
    • When exponent is 1 it will be coefficient(variable) => 4x
    • When coefficient is 1 it will be (variable)^exponent => x^2
  • Polynomials are one variable only
  • Use of external libraries are forbidden
  • The coefficient and variable input can be positive and negative numbers.

Test cases

  • ("3x^3-5x^2+2x-10", 5) => 250
  • ("10x^4-5x^3-10x^2+3x+50", 3) => 644
  • ("10x+20", 10) => 120
  • ("-20x^2+20x-50", -8) => -1490
  • ("9", 5) => 9
  • ("8x^2+5", 0) => 5

Update

  • Polynomial format will always be coefficient(variable)^exponent => 4x^2 except :
    • When exponent is 1 it will be coefficient(variable) => 4x
    • When coefficient is 1 it will be (variable)^exponent => x^2
  • Removed the rule of negative exponent. My mistake. A valid polynomial does not contain negative exponent
  • An exponent of 0 would be just coefficient
  • Added test case for input 0

This is , so the shortest answer in bytes win.

\$\endgroup\$
  • 3
    \$\begingroup\$ How flexible is the input format? Instead of 3x^3-5x^2+2x-10 can we input 3*x^3-5*x^2+2*x-10? Or [3 -5 2 -10]. [3 2 1 0]? \$\endgroup\$ – Luis Mendo Jun 4 '18 at 13:59
  • 1
    \$\begingroup\$ @Arnauld Yes... \$\endgroup\$ – Luis felipe De jesus Munoz Jun 4 '18 at 20:04
  • 4
    \$\begingroup\$ What is an "external library" and how is it fair, compared to languages who have "eval" already implemented as a feature? \$\endgroup\$ – Olivier Grégoire Jun 4 '18 at 23:02
  • 1
    \$\begingroup\$ My apologies I haven't use my pc since yesterday. I have updated the challenge with the suggestions you gave me. Please take a look at it and reopen it if everything is ok. \$\endgroup\$ – Luis felipe De jesus Munoz Jun 5 '18 at 12:32
  • 1
    \$\begingroup\$ Please merge the "Update" part. \$\endgroup\$ – user202729 Jun 5 '18 at 13:39

19 Answers 19

12
\$\begingroup\$

JavaScript (ES7), 48 bytes

Based upon a suggestion from @RickHitchcock

Expects X in uppercase. Takes input in currying syntax (p)(X).

p=>X=>eval(p.replace(/[X^]/g,c=>c<{}?'*X':'**'))

Try it online!


JavaScript (ES7), 49 bytes

Same approach as @DeadPossum. Takes input in currying syntax (p)(x).

p=>x=>eval(p.split`x`.join`*x`.split`^`.join`**`)

Try it online!

\$\endgroup\$
  • 1
    \$\begingroup\$ I think you can save a couple bytes by using replace: p=>x=>eval(p.replace(/[x^]/g,a=>a>f?'*x':'**')) \$\endgroup\$ – Rick Hitchcock Jun 4 '18 at 19:50
  • \$\begingroup\$ @RickHitchcock I can't use a reference to f unless it's included in the byte count, at the cost of the 2 bytes that are supposed to be saved. I like this method, though. There might be a way to save a byte or two by revamping it somehow. \$\endgroup\$ – Arnauld Jun 4 '18 at 20:00
  • \$\begingroup\$ Oh, of course. Hmm. \$\endgroup\$ – Rick Hitchcock Jun 4 '18 at 20:02
  • 2
    \$\begingroup\$ @RickHitchcock If we can take X in uppercase, then we can do a<{}?'*X':'**', saving a byte. Hence my question to the OP. \$\endgroup\$ – Arnauld Jun 4 '18 at 20:03
  • \$\begingroup\$ cant handle x alone \$\endgroup\$ – l4m2 Jun 7 '18 at 9:01
8
\$\begingroup\$

Python 2, 54 bytes

-2 bytes thanks to Jo King

-5 bytes thanks to Arnauld

lambda p,x:eval(p.replace('^','**').replace('x','*x'))

Try it online!

\$\endgroup\$
8
\$\begingroup\$

Python 3, 53 50 48 bytes

edit: -5 bytes thanks to Dennis !

lambda p,x:eval(p.translate({94:"**",120:"*x"}))

Try it online!

Used translate to avoid chaining replace calls; Python 3's version of translate is less awkward than its predecessor's.

\$\endgroup\$
  • \$\begingroup\$ "*(%d)"%x can become "*(x)". \$\endgroup\$ – Dennis Jun 4 '18 at 14:11
  • \$\begingroup\$ Thank you, I hadn't event figured out x was in my eval scope ! I'll update. \$\endgroup\$ – etene Jun 4 '18 at 15:36
  • 1
    \$\begingroup\$ Actually, since x is no longer a string representation, "*x" works as well. \$\endgroup\$ – Dennis Jun 4 '18 at 15:56
  • \$\begingroup\$ Even better ! Thanks again. \$\endgroup\$ – etene Jun 4 '18 at 18:00
5
\$\begingroup\$

R, 44 bytes

function(f,x)eval(parse(t=gsub("x","*x",f)))

Try it online!

Fairly straightforward with R. Replace nx with n*x and then eval the parsed string. x is used as this is how we name the second argument.

The eval function could even be used more directly with a properly formatted first argument, and other formal arguments (y, z, etc.) could be easily added:

R, 20 bytes (non-competing)

function(f,x)eval(f)

Try it online!

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

Japt 2.0, 13 bytes

OvUd^'*²'x"*V

Try it.

Explanation:

OvUd^'*²'x"*V
              U = Implicit first input
              V = Implicit second input

Ov            Eval:
  Ud            In U, replace:
    ^             "^" with:
     '*²            "**"
        'x        "x" with:
          "*V       "*V"
\$\endgroup\$
4
\$\begingroup\$

Wolfram Language (Mathematica), 22 bytes

ToExpression@#/.x->#2&

Try it online!

\$\endgroup\$
3
\$\begingroup\$

JavaScript (Node.js), 113 108 bytes

_=>x=>_.match(/-?(?:[x\d]+|\^?)+/g).reduce((a,b)=>b.split`x`[0]*(~b.indexOf`x`?x**(b.split`^`[1]||1):1)+a,0)

Try it online!

Thanks to @Arnauld


Since the best JS solution so far by @Arnauld (49 bytes) has already been posted and it uses eval, I decided to use Regex and reduce instead of that.

Pretty lengthy compared to his though.

Explanation :

A =>                            // lambda function accepting argument 1 
    x =>                        // argument number 2 (currying syntax used)
        A.match(                // this matches all instance of what comes next 
                                // and converts to array
       /[-]?(?:[x\d]+|\^?)+/g)  // regexp for -ve sign , variable number and ^ sign 
            .reduce((a, b) =>   // reduce the array to single (take 2 params a,b)
                b.split `x`     // split b at instances of `x` 
                        [0]     // and select the first instance 
                * (b.indexOf`x` // multiply that by value of index of x in b 
                    > 0 ?       // if it is greater than 0 then 
                x **            // multiplication will be with x raised to power
               (l = b.split `^` // set variable split b at every `x` 
                   [1]||1       // choose first index otherwise set to one
                )               // this is what x is raised to the power 
                : 1)            // in the case x is not present multiply by 1
                + a,            //  add value of `a` to that value 
        0)                      // in case no reduce is possible set value to 0

\$\endgroup\$
  • \$\begingroup\$ This currently fails on the last test case (should be 0.25). You can save a few bytes by using - instead of [-], ~b.indexOf`x` instead of b.indexOf`x`>0 and removing l= which is not used. (But this doesn't fix the bug.) \$\endgroup\$ – Arnauld Jun 4 '18 at 20:39
  • \$\begingroup\$ @Arnauld: Thanks. No idea why it does that, will see what the problem \$\endgroup\$ – Muhammad Salman Jun 4 '18 at 20:59
  • \$\begingroup\$ Well, the problem is that your regex splits 1x^-2 on the -. \$\endgroup\$ – Arnauld Jun 4 '18 at 21:03
3
\$\begingroup\$

05AB1E, 16 19 bytes

„*(I')J'xs:'^„**:.E

+3 bytes as bug-fix for negative input x.

.E (Run as Batch code) has been replaced with Run as Python eval in this latest commit of @Adnan, but this version isn't on TIO yet. @Mr.Xcoder tested it on his local (latest version) 05AB1E to verify it's working.
See this version without .E to see how it converted the expression string.

Explanation:

„*I')J'xs:    # Replace all "x" with "*(n)" (where `n` is the input-integer)
              #  i.e. 5 and 3x^3-5x^2+2x-10 → 3*(5)^3-5*(5)^2-2*(5)-10
'^„**:        # Replace all "^" with "**"
              #  i.e. 3*(5)^3-5*(5)^2-2*(5)-10 → 3*(5)**3-5*(5)**2-2*(5)-10
.E            # Evaluate as Python-eval
              #  i.e. 3*(5)**3-5*(5)**2-2*(5)-10 → 250

Alternative 25 28 bytes program that works on the current version of TIO:

„*(I')J'xs:'^„**:“…¢(“s')J.e

Try it online.

Explanation:

„*(I')J'xs:'^„**:    # Same as explained above
“…¢(“                # Literal string "print("
     s               # Swap both
      ')             # Literal character ")"
        J            # Join everything together
                     #  i.e. 3*(5)**3-5*(5)**2-2*(5)-10 → print(3*(5)**3-5*(5)**2-2*(5)-10)
.e                   # Run as Python code
                     #  i.e. print(3*(5)**3-5*(5)**2-2*(5)-10) → 250

“…¢(“ is the string print(, because:

  • and starts and ends the compressed string
  • …¢ is equal to 0426 because it looks at the indices in the info.txt file, where has index 4, and ¢ has index 26.
  • This index 0426 is then used in the dictionary-file, where line 427 (index 426) is the word it fetches, which is print in this case.
  • The ( doesn't have an index in the info.txt file, so it is interpret as is.
\$\endgroup\$
2
\$\begingroup\$

JavaScript (Node.js), 143 bytes

I know there are better answers but I wanted to do it without using eval

(_,x)=>_.match(/[+-]?(?:[a-z0-9.]+|\^-?)+/gi).reduce((a,b)=>~~(b.split('x')[0])*(b.indexOf('x')>0?Math.pow(x,(l=(b.split('^')[1]))?l:1):1)+a,0)

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Your regex doesn't need [a-z0-9.] does it? The only letter that can appear is x. Any why .? You don't need to handle non-integer coefficients or exponents. \$\endgroup\$ – Peter Cordes Jun 5 '18 at 4:58
2
\$\begingroup\$

Physica, 35 bytes

->e;x:Eval@Replace[e;"x";f"*({x})"]

Try it online!

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

Jelly, 21 bytes

ṣ”^j⁾**ṣ”xjØ(j”*;Ʋ}ŒV

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Due to operator precedence, this doesn't work for ("-20x^2+20x-50", -8). \$\endgroup\$ – Dennis Jun 4 '18 at 18:15
  • \$\begingroup\$ @Dennis Adjusted accordingly. \$\endgroup\$ – Erik the Outgolfer Jun 4 '18 at 18:51
2
\$\begingroup\$

Java 8, 150 149 148 bytes

n->s->new javax.script.ScriptEngineManager().getEngineByName("JS").eval(s.replace("x","*"+n).replaceAll((s="(\\-?\\d+)")+"\\^"+s,"Math.pow($1,$2)"))

Not sure if it's possible to have a currying lambda function that throws an Exception. If it is, 1 byte can be saved changing (s,n)-> to n->s->. -1 byte thanks to @OlivierGrégoire for showing me how to do this.

Try it online.

Explanation:

n->s->     // Method with integer and String parameters and Object return-type
  new javax.script.ScriptEngineManager().getEngineByName("JS")
            //  Use a JavaScript engine
   .eval(s  //  And eval the input
      .replace("x","*"+n)
            //   After all 'x' has been replaced with '*n'
            //   (where `n` is the input-integer)
      .replaceAll((s="(\\-?\\d+)")+"\\^"+s,"Math.pow($1,$2)"))
            //   And all `A^B` have have been replaced with `Math.pow(A,B)`
            //   (where both `A` and `B` are integers)

Unfortunately the JavaScript eval doesn't support **, so I have to use a longer replace to convert it to Math.pow instead..

\$\endgroup\$
  • \$\begingroup\$ JavaScript does support ** (ES7+), why does this not support that ? \$\endgroup\$ – Muhammad Salman Jun 4 '18 at 14:16
  • \$\begingroup\$ Also is there no eval in java. That can't be right ? \$\endgroup\$ – Muhammad Salman Jun 4 '18 at 14:17
  • \$\begingroup\$ @MuhammadSalman Nope, Java has no eval. And I think this builtin JavaScript-eval I can use with ScriptEngineManager hasn't been updated in the Java JDK for years, so it doesn't support ES7+.. \$\endgroup\$ – Kevin Cruijssen Jun 4 '18 at 14:20
  • \$\begingroup\$ Man, java sucks, no eval why ? Okay why hasn't it been updated ? \$\endgroup\$ – Muhammad Salman Jun 4 '18 at 14:21
  • \$\begingroup\$ @MuhammadSalman I dunno.. You'll have to ask the creators of Java that question. ;) \$\endgroup\$ – Kevin Cruijssen Jun 4 '18 at 14:26
2
\$\begingroup\$

TI-Basic, 6 bytes

Prompt X:expr(Ans

Expression is taken as argument and X is entered during runtime. Alternatively 8 bytes without expr:

Prompt X,u:u

Here both arguments are entered at runtime.

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

Octave, 47 38 37 bytes

Saved a lot of bytes by taking the second input as a string instead of a number.

@(x,c)eval(strrep(x,'x',['*(',c,41]))

Try it online!

Explanation:

Fairly straight forward: Replace x by (c) , where c is the second input, and evaluate. The paretheses are necessary because in Octave -8^2 == -64.

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

Ruby, 43 bytes

->s,x{eval s.gsub /[x^]/,?x=>"*x",?^=>"**"}

Try it online!

\$\endgroup\$
  • \$\begingroup\$ Nice approach with hash replacement, but straight two gsubs are even shorter \$\endgroup\$ – Kirill L. Jun 4 '18 at 13:34
1
\$\begingroup\$

Perl 5 -pl, 35 bytes

s/\^/**/g;$q=<>;s/x/*($q)/g;$_=eval

Try it online!

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

Ruby, 43 41 bytes

->p,x{eval p.gsub('^','**').gsub'x','*x'}

Try it online!

Saved two bytes thanks to @Mr.Xcoder


Since there isn't a Ruby answer yet I added one. Nvm there was one that used a different approach

Explanation :

->p,x{                    # lambda function that takes two arguments p and x
    eval(                 # eval 
        p.gsub(           # replace all instance of 
            '^' , '**'    # `^` with `**` (use for raised to power of)
        )                 # end gsub
        .gsub(            # start another replace all
            'x' , '*x'    # replace all instances of `x` with `*x`
        )                 # end the replace function
    )                     # end eval function
}                         # end lambda function
\$\endgroup\$
1
\$\begingroup\$

Excel, 36+2 bytes, Non-competing

Evaluating a Text field as a formula is not straight forward in Excel. There is a hidden =EVALUATE() function, that can be called by defining a Name.

In Excel 2007, Formulas > Define Name. Define a Name called E, with Refers to:

=EVALUATE(SUBSTITUTE(A1,"x","*"&B1))

Then, with Formula input in A1, x value in B1, entering =E in C1 returns expected result.

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

Wolfram Language (Mathematica), 19 bytes

(x=#;ToExpression)&

Try it online!

Take input by currying: f[x][expr].

\$\endgroup\$

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.