|
Subject: Re: [xsl] Seeking an elegant XSLT function to check that a pair of numeric ranges are consecutive From: "Dimitre Novatchev dnovatchev@xxxxxxxxx" <xsl-list-service@xxxxxxxxxxxxxxxxxxxxxx> Date: Sat, 25 May 2024 20:24:05 -0000 |
> My guess is that this is not the case with this problem, otherwise they
would have chosen another range delimiter, for example "~".
And in this case the expression becomes:
let $ranges := /*/*/*,
$starts := $ranges/xs:integer(substring-before(. || '~', '~')),
$ends := $ranges/xs:integer(if(contains(., '~')) then
substring-after(., '~')
else .)
return
every $i in 1 to count($starts) -1 satisfies
$ends[$i] eq $starts[$i +1] -1
And one could, of course, parameterise further:
let $ranges := /*/*/*, $d := '~',
$starts := $ranges/xs:integer(substring-before(. || $d, $d)),
$ends := $ranges/xs:integer(if(contains(., $d)) then substring-after(.,
$d)
else .)
return
every $i in 1 to count($starts) -1 satisfies
$ends[$i] eq $starts[$i +1] -1
On Sat, May 25, 2024 at 1:20b/PM Dimitre Novatchev dnovatchev@xxxxxxxxx <
xsl-list-service@xxxxxxxxxxxxxxxxxxxxxx> wrote:
> > This XPath expression is lovely, but what if the start of the range is a
> negative integer?
>
> My guess is that this is not the case with this problem, otherwise they
> would have chosen another range delimiter, for example "~".
>
> Thanks,
> Dimitre
>
> On Sat, May 25, 2024 at 1:13b/PM Jeffrey Greif jgreif@xxxxxxxxxxxxxxxxxxxx
> <xsl-list-service@xxxxxxxxxxxxxxxxxxxxxx> wrote:
>
>> This XPath expression is lovely, but what if the start of the range is a
>> negative integer?
>>
>> On Sat, May 25, 2024 at 11:30b/AM Dimitre Novatchev dnovatchev@xxxxxxxxx
<
>> xsl-list-service@xxxxxxxxxxxxxxxxxxxxxx> wrote:
>>
>>> Here is a pure XPath solution - 7 lines well-formatted expression:
>>>
>>> let $ranges := /*/*/*,
>>> $starts := $ranges/xs:integer(substring-before(. || '-', '-')),
>>> $ends := $ranges/xs:integer(if(contains(., '-')) then
>>> substring-after(., '-')
>>> else .)
>>> return
>>> every $i in 1 to count($starts) -1 satisfies
>>> $ends[$i] eq $starts[$i +1] -1
>>>
>>> Thanks,
>>> Dimitre
>>>
>>> On Sat, May 25, 2024 at 8:51b/AM Roger L Costello costello@xxxxxxxxx <
>>> xsl-list-service@xxxxxxxxxxxxxxxxxxxxxx> wrote:
>>>
>>>> Hi Folks,
>>>>
>>>> I have an XML document that contains a series of records and each
>>>> record contains a numeric range:
>>>>
>>>> <Document>
>>>> <Record>
>>>> <Range>0-2</Range>
>>>> </Record>
>>>> <Record>
>>>> <Range>3-7</Range>
>>>> </Record>
>>>> <Record>
>>>> <Range>8</Range>
>>>> </Record>
>>>> <Record>
>>>> <Range>9-15</Range>
>>>> </Record>
>>>> </Document>
>>>>
>>>> Notice that a "range" is either two integers separated by a dash (e.g.,
>>>> 0-2), or a single integer (e.g., 8).
>>>>
>>>> I need to check the ranges, to ensure that adjacent pairs contain
>>>> ranges that are consecutive. Thus, this pair of ranges:
>>>>
>>>> 0-2, 3-7
>>>>
>>>> is good (i.e., consecutive), but this pair of ranges:
>>>>
>>>> 0-2, 5-8
>>>>
>>>> is bad (i.e., not consecutive).
>>>>
>>>> I wrote an XSLT function that checks a pair of ranges and returns true
>>>> if they are consecutive and false if they are not consecutive.
>>>>
>>>> My function is okay. It seems to work properly. But it's kind of ugly
>>>> and brute-force. I wonder if there is a more elegant solution?
>>>>
>>>> Here is my function:
>>>>
>>>> <xsl:function name="f:do-ranges-connect" as="xs:boolean">
>>>> <xsl:param name="previous-range"/>
>>>> <xsl:param name="current-range"/>
>>>> <xsl:choose>
>>>> <xsl:when test="matches($previous-range,'^[0-9]+$') and
>>>> matches($current-range,'^[0-9]+$')">
>>>> <xsl:value-of select="xs:integer($current-range) eq
>>>> xs:integer($previous-range) + 1"/>
>>>> </xsl:when>
>>>> <xsl:when test="matches($previous-range,'^[0-9]+$') and
>>>> matches($current-range,'^[0-9]+-[0-9]+$')">
>>>> <xsl:variable name="start"
>>>> select="substring-before($current-range,'-')"/>
>>>> <xsl:value-of select="xs:integer($start) eq
>>>> xs:integer($previous-range) + 1"/>
>>>> </xsl:when>
>>>> <xsl:when test="matches($previous-range,'^[0-9]+-[0-9]+$') and
>>>> matches($current-range,'^[0-9]+$')">
>>>> <xsl:variable name="end"
>>>> select="substring-after($previous-range,'-')"/>
>>>> <xsl:value-of select="xs:integer($current-range) eq
>>>> xs:integer($end) + 1"/>
>>>> </xsl:when>
>>>> <xsl:when test="matches($previous-range,'^[0-9]+-[0-9]+$') and
>>>> matches($current-range,'^[0-9]+-[0-9]+$')">
>>>> <xsl:variable name="start"
>>>> select="substring-before($current-range,'-')"/>
>>>> <xsl:variable name="end"
>>>> select="substring-after($previous-range,'-')"/>
>>>> <xsl:value-of select="xs:integer($start) eq
>>>> xs:integer($end) + 1"/>
>>>> </xsl:when>
>>>> <xsl:otherwise>
>>>> <xsl:message>The range strings are
>>>> non-conformant</xsl:message>
>>>> <xsl:value-of select="false()"/>
>>>> </xsl:otherwise>
>>>> </xsl:choose>
>>>> </xsl:function>
>>>>
>>>>
>>>>
>>> XSL-List info and archive <http://www.mulberrytech.com/xsl/xsl-list>
>>> EasyUnsubscribe <http://lists.mulberrytech.com/unsub/xsl-list/1067740>
(by
>>> email)
>>>
>> XSL-List info and archive <http://www.mulberrytech.com/xsl/xsl-list>
>> EasyUnsubscribe <http://lists.mulberrytech.com/unsub/xsl-list/782854> (by
>> email)
>>
>
>
> XSL-List info and archive <http://www.mulberrytech.com/xsl/xsl-list>
> EasyUnsubscribe <http://lists.mulberrytech.com/unsub/xsl-list/782854> (by
> email <>)
| Current Thread |
|---|
|
| <- Previous | Index | Next -> |
|---|---|---|
| Re: [xsl] Seeking an elegant XSLT f, Dimitre Novatchev dn | Thread | [xsl] Re: Seeking an elegant XSLT f, Roger L Costello cos |
| Re: [xsl] Seeking an elegant XSLT f, Dimitre Novatchev dn | Date | [xsl] Re: Seeking an elegant XSLT f, Roger L Costello cos |
| Month |