Ask Your Question

construct a structure

asked 2013-11-26 10:09:38 +0100

gundamlh gravatar image

Dear all,

I want to construct a structured array which has 2 fields storing 2 different data type, one is a float number and the other is a polynomial matrix.

Structured Arrays (and Record Arrays) Can I use this NumPy method or any other else? NumPy doesn't know/understand the data type of a polynomial matrix defined in SAGE.

sage: R.<s> = PolynomialRing(QQ); R
Univariate Polynomial Ring in s over Rational Field
sage: H = matrix(1,2, [(s+5)**2, s]); H
[s^2 + 10*s + 25               s]
sage: H.parent()
Full MatrixSpace of 1 by 2 dense matrices over Univariate Polynomial Ring in s over Rational Field
sage: type(H[0,0])
<type 'sage.rings.polynomial.polynomial_rational_flint.Polynomial_rational_flint'>
sage: sys = np.zeros(1, dtype=[('TF','sage.rings.polynomial.polynomial_rational_flint.Polynomial_rational_flint',(1,2)),('Ts','f4')])
TypeError                                 Traceback (most recent call last)
/home/xxx/Programs/sage-5.10-linux-64bit/local/lib/python2.7/site-packages/sage/all_cmdline.pyc in <module>()
----> 1 sys = np.zeros(Integer(1), dtype=[('TF','sage.rings.polynomial.polynomial_rational_flint.Polynomial_rational_flint',(Integer(1),Integer(2))),('Ts','f4')])

TypeError: data type "sage.rings.polynomial.polynomial_rational_flint.Polynomial_rational_flint" not understood

Thanks in advance!

edit retag flag offensive close merge delete

3 Answers

Sort by ยป oldest newest most voted

answered 2013-11-29 09:24:06 +0100

niles gravatar image

Unless you need something special about structured arrays, you could just define a new object class:

sage: class UsefulData(SageObject):
....:     def __init__(self,my_float,my_matrix):
....:         self.float = my_float
....:         self.matrix = my_matrix

(I did this at a sage command prompt, but it's better in a notebook cell or in a separate file attached to the sage session. That way you can easily edit and update the class as you do more and more sophisticated things with it.)

sage: R.<s> = PolynomialRing(QQ); R
Univariate Polynomial Ring in s over Rational Field

sage: d1 = UsefulData(pi.n(),matrix([[1, s],[s^2, -1]]))
sage: d1.float
sage: d1.matrix
[  1   s]
[s^2  -1]

sage: d2 = UsefulData(e.n(),matrix([[s^2, s^3],[s^5, s^7]]))
sage: d2.float
sage: d2.matrix
[s^2  s^3]
[s^5  s^7]

There is a further advantage here: if you want to do something with this data, you can attach functions (methods) to the object class too. If computational time or space is an issue, you can convert the expensive parts to cython classes/attributes.

edit flag offensive delete link more


wow! Thanks! >convert the expensive parts to cython classes/attributes.< .... just use "cpdef" instead of "def" ?

gundamlh gravatar imagegundamlh ( 2013-11-29 14:06:26 +0100 )edit

using cpdef does give some speedup, but there is a lot more you can do too. Just remember that premature optimization is a terrible mistake. Optimization without profiling is usually a waste of time too.

niles gravatar imageniles ( 2013-12-02 08:26:28 +0100 )edit

answered 2013-11-29 11:13:43 +0100

nbruin gravatar image

If you just want to package several data items together and refer to them by a name rather than a numerical index (in which case you could use a list), you can use the python library namedtuple:

You'd end up with something like:

sage: from collections import namedtuple
sage: T=namedtuple('T',['scalar','M'])
sage: t=T(2.0,H)
sage: t
T(scalar=2.00000000000000, M=[s^2 + 10*s + 25               s])
sage: t.scalar
sage: t.M
[s^2 + 10*s + 25               s]

It's meant to be a variant of a tuple so it's immutable (after creation you can't change the attributes). If you need that, you can just write your own class, as Niles points out.

You could also make it a dictionary if you don't mind referring to the field names by string:

sage: d=dict(scalar=2.0,M=H)
sage: d
{'M': [s^2 + 10*s + 25               s], 'scalar': 2.00000000000000}
sage: d['M']
[s^2 + 10*s + 25               s]
edit flag offensive delete link more


Thanks! It is a good idea!

gundamlh gravatar imagegundamlh ( 2013-11-29 13:59:57 +0100 )edit

answered 2013-11-29 05:59:57 +0100

tmonteil gravatar image

Why don't you simply use python lists ?

sage: sys = [my_float, my_matrix]
edit flag offensive delete link more


I'd like to giive a name to each entry. for example, sys.a, sys.b, sys.c, sys.d, sys.ts, sys,x0, sys.size, sys.idelay, ....

gundamlh gravatar imagegundamlh ( 2013-11-29 06:05:03 +0100 )edit

Your Answer

Please start posting anonymously - your entry will be published after you log in or create a new account.

Add Answer

Question Tools


Asked: 2013-11-26 10:09:38 +0100

Seen: 431 times

Last updated: Nov 29 '13