2015年6月10日水曜日

astropy.coordinatesを用いた座標の取り扱い、その4 ― SkyCoodクラスの使用法(上級編)

その4の最後で、SkyCoordオブジェクトの座標系を銀河座標系(galactic)へ変換する方法を紹介しました。一旦この変換を行うと、経度と緯度の座標値は、銀河座標系を表す際の慣習に従ってSkyCoordオブジェクト内で銀系と銀緯に対応した、、というラベルが付けられます。天文学の背景知識を持っているユーザーにとっては、(l, b) だけで何を意味しているか即座にわかると思いますが、SkyCoordオブジェクトには、(l, b) の意味も保存されており、状況に応じて適宜情報を取り出すことができます。

>>> sc_gal.representation_component_names
OrderedDict([(u'l', u'lon'), (u'b', u'lat'), (u'distance', u'distance')])

>>> sc_gal.representation_component_units
OrderedDict([(u'l', Unit("deg")), (u'b', Unit("deg"))])

>>> sc_gal.representation
<class 'astropy.coordinates.representation.SphericalRepresentation'>


上記のようなコマンドラインによって、(l, b) が経度と緯度を表していること、(l, b) の単位が度で有ること、直交座標系ではなく球面座標系であることが確認できます。また、上記で使用した representation_component_names という attribute を使うと、SkyCoodオブジェクトの中で使用する座標値の独自の呼称を定義することもできます。

別の重要な attribute としては、frame_attr_names があります。SkyCoordオブジェクトを作成する際、SkyCoordオブジェクトの中でどのようなパラメータが設定可能か確認したい場合があります。この attribute を使うと、簡単に未設定のパラメータを調べることができます。

>>> sc_fk4 = SkyCoord(1, 2, frame='fk4', unit='deg')
>>> sc_fk4.get_frame_attr_names()  
{u'equinox': 

明示的にパラメータを設定していない場合はデフォルト値が設定される場合もあります。上の例では、1行目でFK4座標系におけるSkyCoordオブジェクトを定義していますが、ユーザー側で完全に全パラメータを明示的に定義するには、equinoxobstime というパラメータに値を与える必要があることが分かります。

SkyCoordオブジェクトのパラメータ設定を行う際に若干ややこしのは、SkyCoordオブジェクトが、frameオブジェクトなど、いくつかの別のオブジェクトを土台として設計されていることです。このため、例えばSkyCoordオブジェクトの attribute で実行できる作業が、他の attribute に内包される別の attribute でも実行できてしまう場合があります。以下に例を示します。


>>> sc.frame
<ICRS Coordinate: (ra, dec) in deg
    (1.0, 2.0)>

>>> sc.has_data is sc.frame.has_data
True

>>> sc.frame.  
sc.frame.cartesian                           sc.frame.ra
sc.frame.data                                sc.frame.realize_frame
sc.frame.dec                                 sc.frame.represent_as
sc.frame.default_representation              sc.frame.representation
sc.frame.distance                            sc.frame.representation_component_names
sc.frame.frame_attr_names                    sc.frame.representation_component_units
sc.frame.frame_specific_representation_info  sc.frame.representation_info
sc.frame.get_frame_attr_names                sc.frame.separation
sc.frame.has_data                            sc.frame.separation_3d
sc.frame.is_frame_attr_default               sc.frame.shape
sc.frame.is_transformable_to                 sc.frame.spherical
sc.frame.isscalar                            sc.frame.time_attr_names
sc.frame.name                                sc.frame.transform_to
>>> sc.frame.name
'icrs'

この様に、has_data というSkyCoord自身の attribute でも frame という attribute以下に存在する、has_data でも全く同じ結果が得られます。このような性質は、知っておくと、利用方法によっては便利な場合もあります。

座標変換

座標変換については、実際に天文学のデータを扱う際に重要な項目でもあるので、場所を改めて詳しく紹介します。ここでは、SkyCoordクラスの概要の一部として、簡単な例をいくか紹介しておきます。

>>> from astropy.coordinates import FK5
>>> sc = SkyCoord(1, 2, frame='icrs', unit='deg')
>>> sc.galactic  
<SkyCoord (Galactic): (l, b) in deg
    (99.6378552814, -58.7096929334)>

>>> sc.transform_to('fk5')  # sc.fk5、sc.transform_to(FK5)としても同様の結果が得られます。  
<SkyCoord (FK5: equinox=J2000.000): (ra, dec) in deg
        (1.00000655566, 2.00000243092)>

>>> sc.transform_to(FK5(equinox='J1975'))  # FK5において分点を変更しています。  
<SkyCoord (FK5: equinox=J1975.000): (ra, dec) in deg
        (0.679672818323, 1.86083014099)>

2つのSkyCoordオブジェクトがあった時、2つのオブジェクト間で座標系を一致させる操作は次のような方法で簡単に行えます。

>>> sc2 = SkyCoord(3, 4, frame='fk4', unit='deg', obstime='J1978.123', equinox='B1960.0')
>>> sc.transform_to(sc2) 
<SkyCoord (FK4: equinox=B1960.000, obstime=J1978.123): (ra, dec) in deg
    (0.48726331438, 1.77731617297)>

球面座標以外の座標の利用

ここまでの例では、ずっと球面座標を使ってきました。SkyCoordに組み込まれている座標系ではデフォルトが球面座標なので、球面座標の扱いを知っていれば、実際多くの天文学上の仕事を処理することができます。しかし、球面座標以外にも、直交座標や円柱座標の扱い方を知っておくと便利な場面は少なくありません。ここでは、SkyCoordオブジェクトで使用する座標をどうやって変更するのか簡単に紹介します。座標に関するより詳しい説明は、Using and Designing Coordinate Representationsを見て下さい。

初期化

SkyCoordオブジェクトの座標を扱う際に必要なことは、以下の実例を見ればほぼ十分だと思います。座標を初期化するのに必要なのは、representationというキーワードに、使用する座標を書き込むだけです。直交座標を使う場合の例は以下のとおりです。

>>> c = SkyCoord(x=1, y=2, z=3, unit='kpc', representation='cartesian')
>>> c
<SkyCoord (ICRS): (x, y, z) in kpc
    (1.0, 2.0, 3.0)>
>>> c.x, c.y, c.z
(<Quantity 1.0 kpc>, <Quantity 2.0 kpc>, <Quantity 3.0 kpc>)
他に、円柱座標を使ったり、各座標軸の単位を変更したりするには以下のようにします。
>>> SkyCoord(1, 2*u.deg, 3, representation='cylindrical')
<SkyCoord (ICRS): (rho, phi, z) in (, deg, )
    (1.0, 2.0, 3.0)>

>>> SkyCoord(rho=1*u.km, phi=2*u.deg, z=3*u.m, representation='cylindrical')
<SkyCoord (ICRS): (rho, phi, z) in (km, deg, m)
    (1.0, 2.0, 3.0)>

>>> SkyCoord(rho=1, phi=2, z=3, unit=(u.km, u.deg, u.m), representation='cylindrical')
<SkyCoord (ICRS): (rho, phi, z) in (km, deg, m)
    (1.0, 2.0, 3.0)>

>>> SkyCoord(1, 2, 3, unit=(None, u.deg, None), representation='cylindrical')
<SkyCoord (ICRS): (rho, phi, z) in (, deg, )
    (1.0, 2.0, 3.0)>

SkyCoordオブジェクトのフォーマットを一般的な形で書き下すと以下のようになります。

SkyCoord(COORD, [FRAME | frame=FRAME], [unit=UNIT], [representation=REPRESENTATION],
         keyword_args ...)
SkyCoord(COMP1, COMP2, [COMP3], [FRAME | frame=FRAME], [unit=UNIT],
         [representation=REPRESENTATION], keyword_args ...)
SkyCoord([FRAME | frame=FRAME], =COMP1, =COMP2,
         =COMP3, [representation=REPRESENTATION], [unit=UNIT],
         keyword_args ...)