表元素#

VOTable文件可以包含 RESOURCE 元素,每个元素都可以包含一个或多个 TABLE 元素的 TABLE 元素包含数据数组。

到达 TABLE 元素,可以在 VOTABLE 文件::

for resource in votable.resources:
    for table in resource.tables:
        # ... do something with the table ...
        pass

但是,如果资源的嵌套结构不重要,则可以使用 iter_tables 要返回所有表的简单列表:

for table in votable.iter_tables():
    # ... do something with the table ...
    pass

最后,如果希望文件中只有一个表,那么使用它可能最方便 get_first_table ::

table = votable.get_first_table()

或者,有一种方便的方法来解析VOTable文件并在一个步骤中返回第一个表:

from astropy.io.votable import parse_single_table
table = parse_single_table("votable.xml")

从一个 TableElement 对象,则可以在 array 成员变量::

data = table.array

此数据是 numpy 记录数组。

列的名称来自 IDname 的属性 FIELD 中的元素 VOTABLE 文件。

假设我们有 FIELD 具体如下:

<FIELD ID="Dec" name="dec_targ" datatype="char" ucd="POS_EQ_DEC_MAIN"
       unit="deg">
 <DESCRIPTION>
  representing the ICRS declination of the center of the image.
 </DESCRIPTION>
</FIELD>

备注

VOTable映射 nameID 属性到 numpy D型 namestitles 非常令人困惑。

在VOTable中, ID 保证是唯一的,但不是必需的。 name 不保证是唯一的,但是必需的。

numpy 记录数据类型, names 必须是唯一的,并且是必需的。 titles 不是必需的,也不要求是唯一的。

因此,VOTable的 ID 最接近于 numpynames ,和VOTable的 name 最接近于 numpytitles . 但是,在某些情况下 ID 未提供,a numpy name 将基于VOTable生成 name . 不幸的是,VOTable字段没有既唯一又必需的属性,这是唯一标识列的最方便的机制。

在从 astropy.io.votable.tree.TableElement 对象添加到一个 astropy.table.Table 对象,则可以指定是否优先考虑 nameID 属性来命名列。默认情况下, ID 会被优先考虑。给予 name 首选项,则传递关键字参数 use_names_over_ids=True **

>>> votable.get_first_table().to_table(use_names_over_ids=True)

可以使用以下方法从记录数组中提取此数据列:

>>> table.array['dec_targ']
array([17.15153360566, 17.15153360566, 17.15153360566, 17.1516686826,
       17.1516686826, 17.1516686826, 17.1536197136, 17.1536197136,
       17.1536197136, 17.15375479055, 17.15375479055, 17.15375479055,
       17.1553884541, 17.15539736932, 17.15539752176,
       17.25736014763,
       # ...
       17.2765703], dtype=object)

或相当于:

>>> table.array['Dec']
array([17.15153360566, 17.15153360566, 17.15153360566, 17.1516686826,
       17.1516686826, 17.1516686826, 17.1536197136, 17.1536197136,
       17.1536197136, 17.15375479055, 17.15375479055, 17.15375479055,
       17.1553884541, 17.15539736932, 17.15539752176,
       17.25736014763,
       # ...
       17.2765703], dtype=object)

数据类型映射#

由指定的数据类型 FIELD 元素映射到 numpy 根据下表键入:

VOTABLE类型

NumPy类型

布尔

地下一层

一点

地下一层

无符号字节

u1

字符( 可变长度

O-A型 bytes() 对象。

字符( 固定长度

S

独角兽( 可变长度

O-A型 str 对象

独角兽( 固定长度

U

短的

I2

利息

i4号

长的

十八

浮动

4层

双重的

8楼

漂浮物

第八章

双重复合体

c16型

如果字段是固定大小的数组,则数据存储为 numpy 固定大小数组。

如果数组的大小是一个变量, arraysize 包含“*”),则单元格将包含 numpy 价值观。每个值可以是数组或标量,具体取决于 arraysize 说明符。

检查字段类型#

若要查找有关表中某个字段的更多信息,可以使用 get_field_by_id 方法,该方法返回 Field 具有给定ID的。

要查找有关字段的更多信息,请执行以下操作:

>>> field = table.get_field_by_id('Dec')
>>> field.datatype
'char'
>>> field.unit
'deg'

备注

不应更改字段描述符。若要更改列集,请将表转换为 astropy.table.Table ,进行更改,然后将其转换回原处。

从头开始构建新表#

还可以构建一个新表,定义一些字段数据类型,并用数据填充它。

要从VOTable文件生成新表,请执行以下操作:

from astropy.io.votable.tree import VOTableFile, Resource, TableElement, Field

# Create a new VOTable file...
votable = VOTableFile()

# ...with one resource...
resource = Resource()
votable.resources.append(resource)

# ... with one table
table = TableElement(votable)
resource.tables.append(table)

# Define some fields
table.fields.extend([
        Field(votable, name="filename", datatype="char", arraysize="*"),
        Field(votable, name="matrix", datatype="double", arraysize="2x2")])

# Now, use those field definitions to create the numpy record arrays, with
# the given number of rows
table.create_arrays(2)

# Now table.array can be filled with data
table.array[0] = ('test1.xml', [[1, 0], [0, 1]])
table.array[1] = ('test2.xml', [[0.5, 0.3], [0.2, 0.1]])

# Now write the whole thing to a file.
# Note, we have to use the top-level votable file object
votable.to_xml("new_votable.xml")

缺少值#

表中的任何值都可能“丢失”。 astropy.io.votable 存储为 numpy 每个中的掩码数组 TableElement 举个例子。这就像一个普通的 numpy 掩码数组,可变长度字段除外。对于这些字段,列的数据类型为“Object”和另一个 numpy 掩码数组存储在那里。因此,对可变长度列的操作不起作用-这是因为不直接支持可变长度列 numpy 掩码数组。