{"action":"created","issue":{"url":"https://api.github.com/repos/symengine/symengine/issues/478","labels_url":"https://api.github.com/repos/symengine/symengine/issues/478/labels{/name}","comments_url":"https://api.github.com/repos/symengine/symengine/issues/478/comments","events_url":"https://api.github.com/repos/symengine/symengine/issues/478/events","html_url":"https://github.com/symengine/symengine/issues/478","id":89962761,"number":478,"title":"Write our own mpz_class","user":{"login":"certik","id":20568,"avatar_url":"https://avatars.githubusercontent.com/u/20568?v=3","gravatar_id":"","url":"https://api.github.com/users/certik","html_url":"https://github.com/certik","followers_url":"https://api.github.com/users/certik/followers","following_url":"https://api.github.com/users/certik/following{/other_user}","gists_url":"https://api.github.com/users/certik/gists{/gist_id}","starred_url":"https://api.github.com/users/certik/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/certik/subscriptions","organizations_url":"https://api.github.com/users/certik/orgs","repos_url":"https://api.github.com/users/certik/repos","events_url":"https://api.github.com/users/certik/events{/privacy}","received_events_url":"https://api.github.com/users/certik/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":null,"milestone":null,"comments":11,"created_at":"2015-06-21T21:21:23Z","updated_at":"2015-11-02T19:46:51Z","closed_at":null,"body":"It will be similar to `mpfr_class` and `mpc_class`, that are already implemented in #467.\r\n\r\n`gmpxx` already has an `mpz_class`, but the problem is that if the `gmp` library is compiled with a different c++ compiler (or a different standard library) than SymEngine, then `gmpxx` fails to link (#367, see also #476). Any C++ dependencies must be compiled with the same compiler and we definitely want to optionally depend on many C++ libraries (like Piranha, Boost, primesieve, ...), so in general, we need to require to use the same C++ compiler anyway, there is no way around it.\r\n\r\nHowever, `gmp` is different, because it is a hard dependency. In other words, if people want to just try SymEngine, they can skip all the other dependencies, but they must have `gmp` installed. And because many people have already hit the gmp linking problem (#367), we need to handle `gmpxx` in a special way. The PR #476 at least fails early if `gmpxx` doesn't work, so that's a step in the right direction, but it doesn't help the user actually install it. Another issue is that sometimes `gmp` is not compiled with C++ wrappers.\r\n\r\nSo the ultimate fix is to not use the `gmp` C++ bindings, and just write our own `mpz_class`. That way, we only depend on the C api, which always works, and so SymEngine is easy to install for anybody, to try it out.\r\n\r\nAnother reason is that we eventually have to use a faster integer implementation anyway (#477), and for example `piranha::integer` is using `mpz_t` directly (i.e. it doesn't use `gmpxx`).\r\n\r\nConclusion: `gmp` is a hard dependency and so we should only use the C api, so that SymEngine is easy to install (in the minimal configuration) on all platforms."},"comment":{"url":"https://api.github.com/repos/symengine/symengine/issues/comments/153137251","html_url":"https://github.com/symengine/symengine/issues/478#issuecomment-153137251","issue_url":"https://api.github.com/repos/symengine/symengine/issues/478","id":153137251,"user":{"login":"bluescarni","id":623038,"avatar_url":"https://avatars.githubusercontent.com/u/623038?v=3","gravatar_id":"","url":"https://api.github.com/users/bluescarni","html_url":"https://github.com/bluescarni","followers_url":"https://api.github.com/users/bluescarni/followers","following_url":"https://api.github.com/users/bluescarni/following{/other_user}","gists_url":"https://api.github.com/users/bluescarni/gists{/gist_id}","starred_url":"https://api.github.com/users/bluescarni/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/bluescarni/subscriptions","organizations_url":"https://api.github.com/users/bluescarni/orgs","repos_url":"https://api.github.com/users/bluescarni/repos","events_url":"https://api.github.com/users/bluescarni/events{/privacy}","received_events_url":"https://api.github.com/users/bluescarni/received_events","type":"User","site_admin":false},"created_at":"2015-11-02T19:46:51Z","updated_at":"2015-11-02T19:46:51Z","body":"@certik My understanding is that in-place operations are faster in their compound form, while multiplication (and possibly division - not sure about it) are slightly faster in binary form. So, provided you have ``a``, ``b`` and ``c`` pre-allocated, the optimal form for ``a = b * c`` should be ``mpz_mul(a,b,c)``.\r\n\r\nAgain, this is what I infer from the GMP manual:\r\n\r\nhttps://gmplib.org/manual/Efficiency.html#Efficiency\r\n\r\nSo with the possible exception of multiplication, it seems like decomposing complex operations in compound forms is the way to go. The code you posted does not incur in extra allocations from the C++ side, but if you had an in-place multiplication in there it looks like internally GMP might make a copy of one of the operands.\r\n"}}