Search code examples
clojure

Returning the terms of a polynomial in clojure


I simply need to write a function that will return a list of terms in a polynomial, so for ex: say we have 3x^4 + 2x^3 + x^2 + x +10 , it will return an output in the form : [coef variable exponent]

My function so far:

(defn terms-of-poly [poly]
    for [x (poly :coefficients)]
    for [y(poly :variables)]
    [x y])


Input:

(let [poly {:variable "y"
            :coefficients [3 2 1 10]}]
    (vec (terms-of-poly poly)))

Output: [[3 "x" 4] [2 "x" 3] [1 "x" 2] [10 "x" 0]]


Solution

  • the solution could look something like this:

    (let [poly {:variable "y"
                :coefficients [3 2 1 0 10]}]
      (mapv vector
            (rseq (:coefficients poly))
            (repeat (:variable poly))
            (range)))
    
    ;;=> [[10 "y" 0] [0 "y" 1] [1 "y" 2] [2 "y" 3] [3 "y" 4]]
    

    it is inverted, but you can reverse it with rseq / reverse

    (notice, i've changed the input, since there is one more member, namely 0x^1)

    more or less the same with list comprehension approach:

    (let [poly {:variable "y"
                :coefficients [3 2 1 0 10]}]
      (for [[pow coeff] (map-indexed vector (rseq (:coefficients poly)))]
        [coeff (:variable poly) pow]))
    
    ;;=> ([10 "y" 0] [0 "y" 1] [1 "y" 2] [2 "y" 3] [3 "y" 4])
    

    you can also filter out coeffs with zero multipliers:

    (let [poly {:variable "y"
                :coefficients [3 2 1 0 10]}]
      (for [[pow coeff] (map-indexed vector (rseq (:coefficients poly)))
            :when (pos? coeff)]
        [coeff (:variable poly) pow]))
    
    ;;=> ([10 "y" 0] [1 "y" 2] [2 "y" 3] [3 "y" 4])
    

    update

    if the order is important (though i guess reversed order should be ok, since every element is identified by it's power), you can do the following for example:

    (defn terms-of-poly [{:keys [variable coefficients]}]
      (map vector
           coefficients
           (repeat variable)
           (range (dec (count coefficients)) -1 -1)))
    
    (let [poly {:variable "y"
                :coefficients [3 2 1 0 10]}]
      (terms-of-poly poly))
    
    ;;=> ([3 "y" 4] [2 "y" 3] [1 "y" 2] [0 "y" 1] [10 "y" 0])