xml – 如何使用XSLT包装一组相邻元素?
发布时间:2020-12-16 07:48:18 所属栏目:百科 来源:网络整理
导读:我有一些 XML ListItem元素,我想用 List包装任何连续的运行元素.所以,源XML看起来像这样: Section HeadHeading/Head ParaBlah/Para ListItemitem 1/ListItem ListItemitem 2/ListItem ListItemitem 3/ListItem ListItemitem 4/ListItem ParaSomething else/
我有一些
XML< ListItem>元素,我想用< List>包装任何连续的运行元素.所以,源XML看起来像这样:
<Section> <Head>Heading</Head> <Para>Blah</Para> <ListItem>item 1</ListItem> <ListItem>item 2</ListItem> <ListItem>item 3</ListItem> <ListItem>item 4</ListItem> <Para>Something else</Para> </Section> 我想把它转换成这样的东西: <Section> <Head>Heading</Head> <Para>Blah</Para> <List> <ListItem>item 1</ListItem> <ListItem>item 2</ListItem> <ListItem>item 3</ListItem> <ListItem>item 4</ListItem> </List> <Para>Something else</Para> </Section> 使用XSLT.我敢肯定这很明显但是我不能在晚上的这个时候解决这个问题.谢谢! 编辑:大多数人都可以安全地忽略这一点. 这个XML: <?xml version="1.0" encoding="UTF-8" standalone="yes"?> <Root> <Story> <Section id="preface"> <ChapterTitle>Redacted</ChapterTitle> <HeadA>Redacted</HeadA> <Body>Redacted</Body> <BulletListItem>Item1</BulletListItem> <BulletListItem>Item2</BulletListItem> <BulletListItem>Item3</BulletListItem> <BulletListItem>Item4</BulletListItem> <HeadA>Redacted</HeadA> <Body>Redacted</Body> <HeadA>Redacted</HeadA> <Body>Redacted</Body> <Body>Redacted<Italic>REDACTED</Italic>Redacted</Body> <BulletListItem>Second list Item1</BulletListItem> <BulletListItem>Second list Item2</BulletListItem> <BulletListItem>Second list Item3</BulletListItem> <BulletListItem>Second list Item4</BulletListItem> <Body>Redacted</Body> </Section> </Story> </Root> 有了这个XSL: <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output omit-xml-declaration="yes" indent="yes"/> <xsl:key name="kFollowing" match="BulletListItem[preceding-sibling::*[1][self::BulletListItem]]" use="generate-id(preceding-sibling::BulletListItem [not(preceding-sibling::*[1][self::BulletListItem])])"/> <xsl:template match="node()|@*" name="identity"> <xsl:copy> <xsl:apply-templates select="node()|@*"/> </xsl:copy> </xsl:template> <xsl:template match="BulletListItem [not(preceding-sibling::*[1][self::BulletListItem])]"> <BulletList> <xsl:call-template name="identity"/> <xsl:apply-templates mode="copy" select="key('kFollowing',generate-id())"/> </BulletList> </xsl:template> <xsl:template match="BulletListItem[preceding-sibling::*[1][self::BulletListItem]]"/> <xsl:template match="BulletListItem" mode="copy"> <xsl:call-template name="identity"/> </xsl:template> </xsl:stylesheet> 当使用Ruby REXML处理并且XML / XSLT生成此XML(输出prettyprint)时: <Root> <Story> <Section id='preface'> <ChapterTitle> Redacted </ChapterTitle> <HeadA> Redacted </HeadA> <Body> Redacted </Body> <BulletList> <BulletListItem> Item1 </BulletListItem> <BulletListItem> Item2 </BulletListItem> <BulletListItem> Item3 </BulletListItem> <BulletListItem> Item4 </BulletListItem> <BulletListItem> Second list Item2 </BulletListItem> <BulletListItem> Second list Item3 </BulletListItem> <BulletListItem> Second list Item4 </BulletListItem> </BulletList> <HeadA> Redacted </HeadA> <Body> Redacted </Body> <HeadA> Redacted </HeadA> <Body> Redacted </Body> <Body> Redacted <Italic> REDACTED </Italic> Redacted </Body> <BulletList> <BulletListItem> Second list Item1 </BulletListItem> </BulletList> <Body> Redacted </Body> </Section> </Story> </Root> 你会看到两个列表被卡在一起,两者之间的位丢失了.不确定这是Ruby库中还是XSLT中的错误.
这个样式表:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:strip-space elements="*"/> <xsl:template match="node()|@*"> <xsl:copy> <xsl:apply-templates select="@*|node()[1]"/> </xsl:copy> <xsl:apply-templates select="following-sibling::node()[1]"/> </xsl:template> <xsl:template match="ListItem"> <List> <xsl:call-template name="ListItem"/> </List> <xsl:apply-templates select="following-sibling::node() [not(self::ListItem)][1]"/> </xsl:template> <xsl:template match="ListItem[preceding-sibling::node()[1] /self::ListItem]" name="ListItem"> <xsl:copy> <xsl:apply-templates select="@*|node()[1]"/> </xsl:copy> <xsl:apply-templates select="following-sibling::node()[1] /self::ListItem"/> </xsl:template> </xsl:stylesheet> 输出: <Section> <Head>Heading</Head> <Para>Blah</Para> <List> <ListItem>item 1</ListItem> <ListItem>item 2</ListItem> <ListItem>item 3</ListItem> <ListItem>item 4</ListItem> </List> <Para>Something else</Para> </Section> 编辑3:使用条带空间来实现它的本质. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |