我正在构建一个处理大量 XML 文件的过程,查找 CALS 模型表(大多数文件至少包含一个),然后将表格数据存储回数据库。在第一种情况下,这些表中的许多表会有不同的结构,但我想使用数据库来分析结构的共性。我在下面列出了来自示例文件的(不完整的)摘录。
<table frame="none">
<tgroup cols="6" colsep="0" rowsep="0">
<colspec colname="1" colnum="1" colwidth="127pt" align="center"/>
<colspec colname="2" colnum="2" colwidth="39pt" align="center"/>
<colspec colname="3" colnum="3" colwidth="30pt" align="center"/>
<colspec colname="4" colnum="4" colwidth="33pt" align="center"/>
<colspec colname="5" colnum="5" colwidth="33pt" align="center"/>
<colspec colname="6" colnum="6" colwidth="87pt"/>
<thead>
<row valign="bottom">
<entry align="center">Product</entry>
<entry>SKU</entry>
<entry>Length</entry>
<entry>Depth</entry>
<entry align="center">Weight</entry>
<entry align="center">Remarks</entry>
</row>
<row valign="bottom">
<entry></entry>
<entry></entry>
<entry>(m)</entry>
<entry>(m)</entry>
<entry align="center">(kg) </entry>
<entry align="center"> </entry>
</row>
</thead>
<tbody>
<row>
<entry align="left" namest="1" nameend="6"><hd4>Whites</hd4></entry>
</row>
<row>
<entry>Albion</entry>
<entry>12345</entry>
<entry>398</entry>
<entry>15.5</entry>
<entry> </entry>
<entry>N/A </entry>
</row>
<row>
<entry>Rotorua</entry>
<entry>12346</entry>
<entry>398</entry>
<entry>15.5</entry>
<entry> </entry>
<entry> </entry>
</row>
<row>
<entry>Quintep</entry>
<entry>12347</entry>
<entry>398</entry>
<entry>15.5</entry>
<entry> </entry>
<entry> </entry>
</row>
由于我知道在此过程中会遇到不同的结构,因此除了将其存储为具有以下属性的实体之外,我无法在数据库中创建将保存所有这些数据的表模式:
- doc_id
- table_id
- row_id
- col_id
- col_name
- col_units
- 入口值
这将允许我将字符串和数值存储为字符串。
在某些情况下,需要的附加属性是上面示例中跨行行中定义的“类别”,位于 tbody/row[1]。在这里,原始文档创建者添加了一个跨越来对紧随其后的行进行分类:
<row>
<entry align="left" namest="1" nameend="6"><hd4>Whites</hd4></entry>
</row>
这些跨行给我带来了一些困难。在它们出现的地方,它们对后面的行进行“分类”,直到出现下一个跨越。
我最初的文档分析表明,与这些跨式相关的表结构有多种可能的“类型”:
- 类型 1. 表格中不出现跨式 - 简单且易于处理
- 类型 2. tbody 中的第一行是一个跨式,并且在 tbody 下方有零个或多个进一步的跨式
- 类型 3. 表包含跨接但不在 tbody 的第一行
类型 3“可以”被视为 2 个单独的表,类型 1 之一(所有行直到但不包括第一个跨行)和类型 2(从第一个跨行向前的所有行)
所以看来解决这个处理问题的关键是确定第一个跨接的位置,将跨接之前的所有内容(零行或多行)视为Type1,并将跨接前的所有内容视为Type 2。
但是我在确定第一个跨骑的位置时遇到了一些困难。我对 1st straddle 的定义——用 Xpath 术语来说——是
tbody/row[entry [@nameend > @namest]][1]
这允许跨式并不总是从第 1 列键入,并且并不总是延伸到最后一列。这两种可能性确实存在于现实世界的数据中。
所以我的问题仍然可以追溯到确定第一跨的位置。
此页面上列出了许多类似的解决方案 http://www.dpawson.co.uk/xsl/sect2/flatfile.html#d5010e13
但是我很难将它们应用到我的实例中。
这样的事情可能会奏效
<xsl:key name="straddles" match="row[entry[@nameend > @namest]]" use="entry/@namest"/>
但我不确定用什么来定义键的@use 属性?
当我尝试定义一个第一跨变量时,我没有定义值传递给 key() 函数?
<xsl:variable name="first-straddle" select="table/tgroup/tbody/row[generate-id() = generate-id(key('straddles',?????))]"/>
如何找到第一个跨栏的位置?
提前致谢
附加说明: ![在浏览器中呈现的示例表的屏幕截图] https://dl.dropboxusercontent.com/u/5065004/Screen%20Shot%202014-02-25%20at%2013.54.08.png 上面的屏幕截图显示了在浏览器中呈现的示例表。跨行“分类”以下行中的数据 - 一直到下一个跨行。@nasmest 和@nameend 属性定义标题跨接的列数,而不是下一个跨接前的行数。后一个值是标记中的 IMPLICIT 并且是我正在搜索的 XPath 语句。前者 - 跨列 - 在标记中是明确的。