Bottom Page

Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
 Generating a polynomial equation
#1
I am new at Python and I found that the best way to learn is to practice. So I decided to write a program that involves generating a polynomial equation from inputting the degree of the polynomial and the corresponding coefficients. For example:

degree = 4
coefficients = 3, 8, 6, 9, and 2

These values should afford the following polynomial equation:

y = 2x^4 + 9x^3 + 6x^2 + 8x^1 + 3x^0

At first, this seemed like an easy task, but I came to a dead end. Angry Any ideas?
Quote
#2
Definitely, you need to create a class Polynom. Instances of that class will be polynomials. Further, you can override arithmetic operations to be able to add two polynomials, multiply polynomials each other etc.
As a starting point, I just wrote some code defining Polynom class.

import sys
import types
from numbers import Number
from abc import ABCMeta, abstractmethod
from collections.abc import Sequence
from itertools import zip_longest


class PolynomBase(metaclass=ABCMeta):
    eps = sys.float_info.epsilon
    
    def __init__(self, coefficients):
        """Initialize a polynom"""

        if isinstance(coefficients, Sequence):
            self.coefficients = tuple(coefficients)
            if not all(map(lambda x: isinstance(x, Number), self.coefficients)):
                raise Exception("Array of coefficients should contain numbers only.")
            if len(self.coefficients) == 0:
                raise Exception("Length of the array of coefficients is zero.")
            if all(map(lambda x: abs(x) < self.eps , self.coefficients)):
                raise Exception("At least one coefficient of the polynom should be greater than eps = {}".format(eps))
        else:
            raise Exception("Array of coeffcients should be of sequence type")
    
    def __repr__(self):
        """Official representation of the polynomial object"""
        return self.__str__()

    def __str__(self):
        """Polynom pretty printing"""
        return ' + '.join("{}x^{}".format(c, i) for i, c in enumerate(self.coefficients))
    
    @abstractmethod
    def calculate(self, x):
        """Returns value of P(x)"""

    @abstractmethod
    def __add__(self, other):
        """Polynom addition"""

#     @abstractmethod
#     def __sub__(self, other):
#         """Polynom substraction"""

#     @abstractmethod
#     def __mul__(self, other):
#         """Polynom multiplication"""

    def __len__(self):
        return self.degree + 1

    @property
    @abstractmethod
    def degree(self):
        """Returns degree of a polynom"""


class Polynom(PolynomBase):
    
    def __init__(self, coefficients):
        super().__init__(coefficients)
    
    def __add__(self, other):
        if isinstance(other, PolynomBase):
            coefficients = []
            for a, b in zip_longest(self.coefficients, other.coefficients, fillvalue=0.0):
                coefficients.append(a + b)
            return Polynom(coefficients)
        elif isinstance(other, Number):
            coefficients = list(self.coefficients)
            coefficients[0] += other
            return Polynom(coefficients)
        raise Exception("Could not add an object of {} to an object of {}".format(type(self), type(other)))

    def __radd__(self, other):
        return self.__add__(other)

    def calculate(self, x):
        res = 0.0
        for p, j in enumerate(self.coefficients):
            res += j * x ** p
        return res
        
    @property
    def degree(self):
        return len(self.coefficients) - 1

    # you need to define additional methods here.
p = Polynom((1,2,3))
print(p)
Output:
1*x^0 + 2*x^1 + 3*x^2
p + 3
Output:
4*x^0 + 2*x^1 + 3*x^2
Quote
#3
Thanks for your detailed response. I am just beginning to learn about classes and find that they are somewhat abstract. I still don't have a good grasp on the topic; everything that I learned thus far has been smooth sailing.
Quote
#4
You can describe polynomial without classes. Any polynomial is defined by its coefficients, so standard data types such as tuple or list can describe a polynomial.

my_polynomial = (1, 2, 3) # we assume that we have a polynomial:  1*x^0 + 2*x + 3*x^2
Further, we need some helper functions that will allow to perform basic operations over such polynomials.

We wish to print the polynomial in human readable form:

def print_polynomial(p, default_argument_name='x'):
    """Print polynomial

    p: a list or a tuple, polynomial coefficients
    """
    result = ''
    for power, coefficient in enumerate(p):
        result += '{}*{}^{} +'.format(coefficient, default_argument_name, power)
    # This is dirty implementation, it doesn't handle +/- signs properly
    print(result[:-1])  # drop `+`
Also, we would like to calculate value of the polynomial at specified point. So, we need to define
a function, e.g. get_polynomial_value,

def get_polynomial_value(p, x):
    """Evaluates polynomial at specified point
    """
    result = 0.0
    for power, coefficient in enumerate(p):
        result += coefficient * x ** power
    return result
You can also wish to be able to export polynomial to Tex/LaTex-format. Thats easy, just write a helper function for this.

def export_to_latex(p):
    """Returns latex-formatted representation of a polynomial"""
    result = r""
    for power, coefficient in enumerate(p):
        result += r'{coefficient}\cdot x^{}'.format(coefficient, power) + '+' if (power != len(coefficient)) else '' # drop `+` for the last polynomial term
    return result
I didn't test these function. You can definitely improve them (e.g. an issue with +/- handling when printing a polynomial), define you own help functions, e.g. define add_polynomials(p1, p2), multiply_polynomials(p1,p1) etc.
Quote

Top Page

Forum Jump:


Users browsing this thread: 1 Guest(s)