Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP]Add apart algorithm for polynomials #1617

Open
wants to merge 8 commits into
base: master
Choose a base branch
from

Conversation

jmig5776
Copy link
Contributor

This PR tends to add apart algorithm corresponding to polynomials just like as we have in sympy but with better benchmarks.
More information will be added soon.

Please suggest ideas or guidance for it.
CC @certik @isuruf

@isuruf-bot
Copy link

isuruf-bot commented Sep 27, 2019

Hi,

I've run clang-format and found that the code needs formatting.
Here's a commit that fixes this. isuruf-bot@00a42b1

To use the commit you can do

curl -o format.diff https://github.com/isuruf-bot/symengine/commit/00a42b1c16eb8cc04535df0bf3c800ab8f4cb348.diff
git apply format.diff

@jmig5776
Copy link
Contributor Author

I created this PR because I have a questions regarding it. Please bear me. Can anyone tell me how exactly I can test my code, i am certainly able to test it but i want to know all procedure to test after editing the code so that i should not miss anything.

And can anybody tell me how I should search some already built function just like i found is_A_Atom here.

@jmig5776
Copy link
Contributor Author

@isuruf can you please please advice me here that how should I frame this class and I went through the expand.cpp also.

@jmig5776
Copy link
Contributor Author

jmig5776 commented Sep 29, 2019

Should it also be based on visitor design pattern?
CC @certik

@certik
Copy link
Contributor

certik commented Sep 30, 2019

@jmig5776 thanks for trying to write a prototype. As a prototype, you can use any design pattern you want, the goal is to get something little working. Then we'll work on designing it well.

To get something little working, try to write a function that accepts a SymEngine expression, converts it to a univariate polynomial (there is code to do that in SymEngine already) and then extracts the coefficients and prints them on the screen. Once you have that, please ping me, and we'll go from there. (The next step would be to try to write apart() for that simple case.)

@jmig5776
Copy link
Contributor Author

Okay I am on it.

@jmig5776
Copy link
Contributor Author

jmig5776 commented Oct 1, 2019

ping @certik
In this the input is basic and it identifies the generators and the polynomial with a single generator gets converted to UExprPoly. And after that, I just extracted the basic polynomial as numerator and denominator.

@jmig5776
Copy link
Contributor Author

jmig5776 commented Oct 2, 2019

@certik I think we might need cancel function here to extract the common parts and then rationalise and make them Add and then multiplying with the common from cancel. What do you think? What should be the next step according to you?

@certik
Copy link
Contributor

certik commented Oct 2, 2019

Good progress, now you have the poly. Now we are at this part of SymPy's apart: https://github.com/sympy/sympy/blob/05f530129287da71600630b6e42f327150943723/sympy/polys/partfrac.py#L128.

Here are the next steps:

  1. Figure out how to extract the coefficients from poly.
  2. Implement cancel.
  3. Implement div.
  4. Implement apart_undetermined_coeffs

And that's pretty much it. Then it just needs to be assembled back into Basic. However, each of these functions will take some time to implement. What you can do is take the simplest of these, perhaps div and see if you can implement that, and get the same results as SymPy. That might not be that difficult.

@certik
Copy link
Contributor

certik commented Oct 2, 2019

You can also try to implement it from here directly, to get something working: https://en.wikipedia.org/wiki/Partial_fraction_decomposition#Procedure

You also need factor_list (factorizes the polynomial), no matter if you translate the sympy's algorithm or write your own.

So I would start with factor_list (and factor). To implement factor is a lot of work. I suggest we use a library for that. Flint (that SymEngine can optionally link to) can do that, here is an example:

https://github.com/wbhart/flint2/blob/c656ed9bcee6264a83924ea882094c78d6ac000d/fmpz_poly_factor/test/t-factor.c#L47

So let's start by writing a factor() function that takes Basic, and internally calls Flint to do it, and converts back to give a list of factors (or a Mul instance).

@certik
Copy link
Contributor

certik commented Oct 2, 2019

In fact SymEngine already implements factors(), here is how to use it:

fac = factors(*UIntPolyFlint::from_dict(

@certik
Copy link
Contributor

certik commented Oct 2, 2019

Here is how to do division using Flint:

b.get_poly().divrem(q, r, a.get_poly());

So try to use these operations (division and factors) to implement the apart using the algorithm at https://en.wikipedia.org/wiki/Partial_fraction_decomposition#Procedure. I think you just construct a linear matrix using the factors, and solve it (SymEngine can do that) to determine the coefficients, and you are set.

@jmig5776
Copy link
Contributor Author

jmig5776 commented Oct 3, 2019

Okay I am on it . Soon will be sending a PR.

@certik
Copy link
Contributor

certik commented Oct 19, 2019

Thanks for trying to figure it out.

@jmig5776
Copy link
Contributor Author

@certik there is no need to thanks. As a open sourcer I want to contribute to make it fastest but truthfully earlier i didn't know development in c++ so in previous two weeks I learnt all the syntaxes and wrote proposal and read about grobner basis. So I might be slow now but will take up the pace in one or two weeks

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants