ASCII-Plot the equation

You are given a polynomial function, in the following format:

$$\x = (c_0 * y^0) + (c_1 * y^1) + (c_2 * y^2) + ... + (c_n * y^n)\$$

where $$\c_n\$$ stands for the coefficient of the $$\n^{th}\$$ power of $$\y\$$

You have to plot the equation on a $$\10 * 10\$$ ASCII matrix. The value must be floored to an integer before plotting. If $$\y < 0\$$ or $$\y > 9\$$, then do not plot. For simplicity, we are assuming the top left corner to be $$\(0,0)\$$.

A . represents an empty space, and * represents a point on the graph. You can choose any characters to represent both of the things as per your convenience but do mention what you use in your answer.

You may take the input as a list/array of coefficients, or, as a string in the above specified format.

Examples:

Input -> x = (1 * y^1)
Output ->
*.........
.*........
..*.......
...*......
....*.....
.....*....
......*...
.......*..
........*.
.........*

Input -> x = (9 * y^0) + (-1 * y^1)
Output ->
.........*
........*.
.......*..
......*...
.....*....
....*.....
...*......
..*.......
.*........
*.........

Input -> x = (0.10 * y^2)
Output ->
*.........
*.........
*.........
*.........
.*........
..*.......
...*......
....*.....
......*...
........*.

Input -> x = (3 * y^1)
*.........
...*......
......*...
.........*
..........
..........
..........
..........
..........
..........


Hint: eval can be helpful here.

Inspired by a clash of code problem from https://www.codingame.com/

• Can we take the function as a black-box function?
Jun 21 at 9:45
• I'm assuming the equation can be taken as a list of coefficients, or similar? Parsing the format shown in the test cases would be unnecessarily involved, and quite likely overshadow the actual task in many languages Jun 21 at 9:45
• @unrelatedstring yes, the input can be taken as a list of coefficients. I have edited the question to include that Jun 21 at 9:47
• Can we return a Boolean matrix with trues indicating the points?
Jun 21 at 9:58
• @Adam That seems reasonable Jun 21 at 10:05

Factor + math.polynomials, 73 bytes

[ 10 iota dup -rot '[ _ polyval 1 /i _ [ = pprint ] with each nl ] each ]


Try it online!

Takes a sequence of coefficients from low to high. polyval handles the actual evaluation of the polynomial; the rest is just data plumbing and output.

1 /i is to convert from a float to integer, as it is shorter than >integer (and floor doesn't produce an integer in Factor [AND 1 /i = is shorter than number= by 1 byte]). I found a locals solution that was the same length, but couldn't save any bytes. You can save 2 bytes by using a modern version of Factor with tuck, but meh.

Prints t for a point on the graph and f for empty space.

APL (Dyalog Unicode), 15 bytes

Full program. Takes list of coefficients in descending order. Returns Binary matrix. Requires 0-based indexing (⎕IO←0).

a∘.=⍨⌊⎕⊥⍨⍪a←⍳10


Try it online!

⍳10indices 0…9

a← store as a

⍪ make into column vector

⎕⊥⍨ prompt for coefficients and evaluate the them as digits in base each-element-of-a

⌊ floor

a∘.=⍨ equality table with a horizontally

Charcoal, 10 bytes

Ｅχ⭆χ⁼λ⌊↨ιθ


Try it online! Takes input as a list of coefficients (in order of highest power of y down to 1) and outputs a binary matrix. Explanation:

 χ          Predefined variable 10
Ｅ           Map over implicit range
χ        Predefined variable 10
⭆         Map over implicit range and join
θ  Input coefficients
ι   Outer index
↨    Evaluate polynomial
⌊     Floor
λ      Inner index
⁼       Do they equal?
Implicitly print


JavaScript (ES7),  87 85 83  81 bytes

Expects an array of coefficients, from lowest to highest.

a=>(g=x=>y>9?'':
*.[x>9?x=++y-y:a.reduce((p,c,i)=>p+c*y**i)^x++?2:1]+g(x))(y=0)


Try it online!

Commented

a => (                   // a[] = input array of coefficients
g = x =>               // g is a recursive function taking x
y > 9 ?                // if this is the end of the graph:
''                   //   stop the recursion
:                      // else:
\n*.[              //   lookup string: 0 = '\n', 1 = '*', 2 = '.'
x > 9 ?            //   if this is the end of the row:
x = ++y - y      //     increment y, set x to 0, yield 0
:                  //   else:
a.reduce(        //     compute P(y)
(p, c, i) =>   //       which is the sum of all
p + c * y ** i //       a[i] * y ** i
) ^ x++          //     test whether floor(P(y)) = x
? 2              //     and yield 2 if it's not
: 1              //     or 1 if it is
] +                  //
g(x)                 //   do a recursive call
)(y = 0)                 // initial call with x = y = 0


J, 15 bytes

-2 thanks to Jonah!

(<.@p.=/])i.@10


Try it online!

Execute the left function with i.@10 (0 1 2 … 9) as the right argument. <.@p. apply polynomial (thanks J for the built-in!) to each i.@10, floor and compare each result to i.@10 with =/.

• (<.@p.=/])i.@10 for 15 Jun 21 at 14:10
• @Jonah Huh. I knew that g@noun f works, but not that f g@noun works, too! Thanks!
– xash
Jun 21 at 14:22
• Yeah, basically g@noun is just shortcut for g@(noun"_) generally. Jun 21 at 14:26

C (gcc), 164 $$\\cdots\$$ 123 111 bytes

Saved 2 bytes thanks to att!!!

y;i;f(l,n,x)float*l,x;{for(y=-1;x=y++<9;i=x>=1&x<11?x:0,puts("         *"+10-i))for(i=n;i--;)x+=l[i]*pow(y,i);}


Try it online!

Uses the space ( ) character for background and an asterisk (*) for plot points.

• 123 bytes
– att
Jun 21 at 23:41
• @att Nice one - thanks! :D Jun 22 at 11:02

Jelly, 108 7 bytes

⁵ḶɓḅḞ=€


Try it online!

-2 bytes because the output format was loosened, then I noticed another golf in the course of writing the explanation

-1 byte because why the hell didn't I already try that?

Input as coefficients in descending order of power, output as binary matrix.

⁵Ḷɓ        Let [0 .. 9] be the right argument to the following dyadic link:
ḅ       evaluate the polynomial at each y in [0 .. 9],
Ḟ      and floor each result.
€    For each result,
=     is it equal to each x in [0 .. 9]?


Stax, 20 bytes

éR▒Å╗←û%╞.A◄→⌐‼²GÑd,


Run and debug it

Very long, partly due to floor not working on integers.

uses 1 and 0 as the display chars.

Python 3, 86 bytes

lambda l,r=range(10):[[i==sum(c*x**n for n,c in enumerate(l))//1for i in r]for x in r]


Try it online!

Takes a list of coefficients in ascending power. Outputs a list of lists of booleans.

p[]x=0;p(s:r)x=x*p r x+s
q f=[[b\$map(subtract y.p f)[x,x+1/4..x+3/4]|y<-n]|x<-n]
b=(['⠀'..]!!).a.map c
n=[0..9]
c x|x<0=[0,0]|x<0.5=[1,0]|x<1=[0,1]|x>0=[0,0]
a[[l,r]]=l*8+r*16
a([l,r]:s)=2*a s+l+r*8


Try it online!

The function q takes a list of polynomial-coefficients and generates braille dot-matrix characters. Example:

x = + (0.0 * y^0) + (0.0 * y^1) + (0.1 * y^2)
⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
⡇⠀⠀⠀⠀⠀⠀⠀⠀⠀
⢱⠀⠀⠀⠀⠀⠀⠀⠀⠀
⠈⡆⠀⠀⠀⠀⠀⠀⠀⠀
⠀⠘⡄⠀⠀⠀⠀⠀⠀⠀
⠀⠀⠘⡄⠀⠀⠀⠀⠀⠀
⠀⠀⠀⠘⢄⠀⠀⠀⠀⠀
⠀⠀⠀⠀⠈⠢⡀⠀⠀⠀
⠀⠀⠀⠀⠀⠀⠑⢄⠀⠀
⠀⠀⠀⠀⠀⠀⠀⠀⠑⢄


Python 3, 112 bytes

def f(l,*m):
for x in range(10):
try:m=[*m,[0]*10];m[x][int(sum(y*x**z for y,z in l))]=1
except:1
return m


Try it online!

-15 bytes thanks to @UnrelatedString

-3 bytes thanks to @ophact

• Function submissions must be reusable, but mutating a list default argument renders this... not. I feel like there is some good way to golf that bit back down, but I'm too tired to think of better than: Jun 21 at 13:44
• tio.run/##pY1BDsIgFET3PQVx9T/… Jun 21 at 13:45
• @UnrelatedString thanks!!! Jun 21 at 14:08
• except:1 instead of except:pass seems to work. Doesn’t do anything as the exp is evaluated
– user100690
Jun 21 at 14:10

Ruby, 78 bytes

->c{(a=0..9).map{|y|a.map{|x|z=1;x==c.reduce{|s,x|s+x*z*=y}.to_i ? ?*:?.}*''}}


Try it online!

Returns an array of 10 strings

Ruby, 67 bytes

->c{(a=0..9).map{|y|a.map{|x|z=1;x==c.reduce{|s,x|s+x*z*=y}.to_i}}}


Try it online!

Return a matrix of booleans

Wolfram Language (Mathematica), 46 43 bytes

0<=#<1&/@(#-r)&/@FromDigits[#,r=0~Range~9]&


Try it online!

Input coefficients in descending order. Returns a 10x10 boolean matrix.