ASKSAGE: Sage Q&A Forum - Individual question feedhttps://ask.sagemath.org/questions/Q&A Forum for SageenCopyright Sage, 2010. Some rights reserved under creative commons license.Wed, 14 Nov 2012 22:14:52 -0600How do I "tidy up" error terms in a matrix?https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/Hi - I have some calculation results in the form of a complex Gram matrix which are all supposed to be integers (or "obvious" algebraic numbers which I know about). However inevitably in the course of creating them as inner products, some "error" terms arise which are of a size of the order of 10^-16 (real and/or complex). Is there an easy way to "clean up" my matrix with some sort of threshold, so that things which differ from a user-specified list of algebraic numbers by less than a tiny amount like 10^-15, are assumed to be the relevant algebraic number? At the moment I'm having to do it by a bunch of hideous if-statement contortions but I'm sure there's a better way!
Many thanks in advance for any help.Mon, 12 Nov 2012 06:20:49 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/Comment by GaryMak for <p>Hi - I have some calculation results in the form of a complex Gram matrix which are all supposed to be integers (or "obvious" algebraic numbers which I know about). However inevitably in the course of creating them as inner products, some "error" terms arise which are of a size of the order of 10^-16 (real and/or complex). Is there an easy way to "clean up" my matrix with some sort of threshold, so that things which differ from a user-specified list of algebraic numbers by less than a tiny amount like 10^-15, are assumed to be the relevant algebraic number? At the moment I'm having to do it by a bunch of hideous if-statement contortions but I'm sure there's a better way!
Many thanks in advance for any help.</p>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18720#post-id-18720thanks - as an example for future reference, I used John's suggestion below in the following form: mat.apply_map( lambda x: (d*abs(x)^2).round()/d ); where I knew that the largest denominator for the abs values was d (one has to be a little more careful with complex entries)Mon, 12 Nov 2012 07:24:02 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18720#post-id-18720Comment by calc314 for <p>Hi - I have some calculation results in the form of a complex Gram matrix which are all supposed to be integers (or "obvious" algebraic numbers which I know about). However inevitably in the course of creating them as inner products, some "error" terms arise which are of a size of the order of 10^-16 (real and/or complex). Is there an easy way to "clean up" my matrix with some sort of threshold, so that things which differ from a user-specified list of algebraic numbers by less than a tiny amount like 10^-15, are assumed to be the relevant algebraic number? At the moment I'm having to do it by a bunch of hideous if-statement contortions but I'm sure there's a better way!
Many thanks in advance for any help.</p>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18722#post-id-18722I've wondered similar things myself. It would be nice to have something like `fnormal` in Maple. Can you apply `round` in some way using a `map` command to help. For example, `round(1+10.^(-16),5)` gives `1.0`.Mon, 12 Nov 2012 06:47:18 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18722#post-id-18722Answer by Volker Braun for <p>Hi - I have some calculation results in the form of a complex Gram matrix which are all supposed to be integers (or "obvious" algebraic numbers which I know about). However inevitably in the course of creating them as inner products, some "error" terms arise which are of a size of the order of 10^-16 (real and/or complex). Is there an easy way to "clean up" my matrix with some sort of threshold, so that things which differ from a user-specified list of algebraic numbers by less than a tiny amount like 10^-15, are assumed to be the relevant algebraic number? At the moment I'm having to do it by a bunch of hideous if-statement contortions but I'm sure there's a better way!
Many thanks in advance for any help.</p>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?answer=14266#post-id-14266Matrices over `ComplexField` don't implement `round()`, unfortunately. But the following variant of John's answer works:
sage: mat = matrix(3, 3, [2+1e-15+i*1e-15]*9)
sage: mat.change_ring(CDF).round()
[2.0 2.0 2.0]
[2.0 2.0 2.0]
[2.0 2.0 2.0]
Tue, 13 Nov 2012 11:13:12 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?answer=14266#post-id-14266Comment by Volker Braun for <p>Matrices over <code>ComplexField</code> don't implement <code>round()</code>, unfortunately. But the following variant of John's answer works:</p>
<pre><code>sage: mat = matrix(3, 3, [2+1e-15+i*1e-15]*9)
sage: mat.change_ring(CDF).round()
[2.0 2.0 2.0]
[2.0 2.0 2.0]
[2.0 2.0 2.0]
</code></pre>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18710#post-id-18710Agreed. I just wanted to point out that matrices over some rings have already a round() method.Tue, 13 Nov 2012 17:01:03 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18710#post-id-18710Comment by GaryMak for <p>Matrices over <code>ComplexField</code> don't implement <code>round()</code>, unfortunately. But the following variant of John's answer works:</p>
<pre><code>sage: mat = matrix(3, 3, [2+1e-15+i*1e-15]*9)
sage: mat.change_ring(CDF).round()
[2.0 2.0 2.0]
[2.0 2.0 2.0]
[2.0 2.0 2.0]
</code></pre>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18704#post-id-18704thanks Volker - that's helpful.Wed, 14 Nov 2012 22:14:52 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18704#post-id-18704Comment by John Palmieri for <p>Matrices over <code>ComplexField</code> don't implement <code>round()</code>, unfortunately. But the following variant of John's answer works:</p>
<pre><code>sage: mat = matrix(3, 3, [2+1e-15+i*1e-15]*9)
sage: mat.change_ring(CDF).round()
[2.0 2.0 2.0]
[2.0 2.0 2.0]
[2.0 2.0 2.0]
</code></pre>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18711#post-id-18711I applied 'real()' and then 'round()' in my answer.Tue, 13 Nov 2012 16:34:22 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18711#post-id-18711Answer by John Palmieri for <p>Hi - I have some calculation results in the form of a complex Gram matrix which are all supposed to be integers (or "obvious" algebraic numbers which I know about). However inevitably in the course of creating them as inner products, some "error" terms arise which are of a size of the order of 10^-16 (real and/or complex). Is there an easy way to "clean up" my matrix with some sort of threshold, so that things which differ from a user-specified list of algebraic numbers by less than a tiny amount like 10^-15, are assumed to be the relevant algebraic number? At the moment I'm having to do it by a bunch of hideous if-statement contortions but I'm sure there's a better way!
Many thanks in advance for any help.</p>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?answer=14258#post-id-14258This will clean things up if the entries are integers. If the entries differ by small amounts from known algebraic numbers, that's more complicated.
sage: mat = matrix(3, 3, [2+1e-15+i*1e-15]*9)
sage: mat
[2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I]
[2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I]
[2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I]
sage: mat.apply_map(lambda x: x.real().round())
[2 2 2]
[2 2 2]
[2 2 2]
sage: mat_Z = mat.apply_map(lambda x: x.real().round())
sage: mat_Z.base_ring()
Integer Ring
Mon, 12 Nov 2012 06:45:56 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?answer=14258#post-id-14258Comment by GaryMak for <p>This will clean things up if the entries are integers. If the entries differ by small amounts from known algebraic numbers, that's more complicated.</p>
<pre><code>sage: mat = matrix(3, 3, [2+1e-15+i*1e-15]*9)
sage: mat
[2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I]
[2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I]
[2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I 2.00000000000000 + 1.00000000000000e-15*I]
sage: mat.apply_map(lambda x: x.real().round())
[2 2 2]
[2 2 2]
[2 2 2]
sage: mat_Z = mat.apply_map(lambda x: x.real().round())
sage: mat_Z.base_ring()
Integer Ring
</code></pre>
https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18721#post-id-18721thanks John - that's certainly a thousand times neater than the mess I had before! The algebraic number thing is almost too good to be true, but maybe someone out there knows a way ... (obviously the list would have to be "restricted" in the sense that the abs vals of the entries would have to be separated by more than twice the error term or something, etc etc)Mon, 12 Nov 2012 07:05:52 -0600https://ask.sagemath.org/question/9528/how-do-i-tidy-up-error-terms-in-a-matrix/?comment=18721#post-id-18721