سؤال

في الأساس لدي قالب صغير يشبه:

<xsl:template name="templt">
    <xsl:param name="filter" />
    <xsl:variable name="numOrders" select="count(ORDERS/ORDER[$filter])" />
</xsl:template>

و أنا أحاول الاتصال باستخدام

<xsl:call-template name="templt">
    <xsl:with-param name="filter" select="PRICE &lt; 15" />
</xsl:call-template>

للأسف يبدو أن تقييم ذلك من قبل القالب يسمى (نحو فعال "كاذبة" يجري تمريرها في) أرفق ذلك في الاقتباس فقط يجعل من سلسلة حرفية بحيث لا يعمل ايضا.لا أحد يعرف إذا ما أحاول أن يحققوه هو ممكن ؟ إذا كان الأمر كذلك هل يمكن أن تلقي بعض الضوء على ذلك ؟ هتافات

هل كانت مفيدة؟

المحلول

وماذا عن ما يلي:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output method="xml" indent="yes"/>

  <xsl:template name="templt">
    <xsl:param name="filterNodeName" />
    <xsl:param name="filterValue" />
    <xsl:variable name="orders" select="ORDERS/ORDER/child::*[name() = $filterNodeName and number(text()) &lt; $filterValue]" />
    <xsl:for-each select="$orders">
      <xsl:value-of select="."/>
    </xsl:for-each>
  </xsl:template>

  <xsl:template match="/">
    <xsl:call-template name="templt">
      <xsl:with-param name="filterNodeName" select="'PRICE'" />
      <xsl:with-param name="filterValue" select="15" />
    </xsl:call-template>
  </xsl:template>
</xsl:stylesheet>

إذا كنت لا تزال ترغب في استخدام معلمة واحدة فقط، هل يمكن أن tokenize في قالب "templt" أولا.

نصائح أخرى

ديفو الجواب هو فكرة جيدة.

ومع ذلك ، فإنه يقيد أي في نهاية المطاف إلى تصفية تحديد اسم الطفل و قيمة.

أنه لأمر جيد أن نعرف أن واحدة يمكن تمرير (ما يصل إلى) وظيفة كمعلمة.هذه قوية جدا يتم تطبيق مفهوم في FXSL -- البرمجة الوظيفية مكتبة XSLT.FXSL هو مكتوب تماما في XSLT نفسها.

هنا هو مناسب سبيل المثال باستخدام وظيفة مرشح/قالب.نحن تمرير مرشح كمعلمة إلى القالب الذي يؤدي التصفية.مرشح يمكن أن يكون أي رمز/المنطق.في هذه الحالة بالذات نحن تمر كما المعلمة إشارة إلى القالب الذي يتحقق إذا كان عدد حتى هو.التحول الكامل النواتج فقط تلك "num" عناصر قيمته هو عدد زوجي.

يمكننا بسهولة جدا تمرير أي مرشح, باستخدام بالضبط نفس الأسلوب:إلى تصفية (الأمم المتحدة)حتى الأرقام, الساحات, الأعداد, ...الخ.

ملاحظة, أن المرء لا يجب أن يكتب على نفسه "مرشح" قالب -- هو مكتوب مرة واحدة و إلى الأبد و التي تقدمها FXSL المكتبة.نتيجة عادة يستخدم فقط <xsl:import /> التوجيه إلى استيراد "تصفية" قالب و العديد من الوظائف المفيدة الأخرى/قوالب التي قدمتها بالفعل FXSL.

التحول أدناه:

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:f="http://fxsl.sf.net/"
xmlns:myIsEven="myIsEven"
>

  <xsl:import href="filter.xsl"/>

  <!-- To be applied on numList.xml -->

  <xsl:output indent="yes" omit-xml-declaration="yes"/>

  <myIsEven:myIsEven/>

  <xsl:template match="/">
    <xsl:variable name="vIsEven"
         select="document('')/*/myIsEven:*[1]"/>

    Filtering by IsEven:
    <xsl:call-template name="_filter">
        <xsl:with-param name="pList" select="/*/*"/>
        <xsl:with-param name="pController" select="$vIsEven"/>
    </xsl:call-template>

  </xsl:template>

  <xsl:template name="myIsEven" mode="f:FXSL"
    match="myIsEven:*">
    <xsl:param name="arg1"/>

    <xsl:if test="$arg1 mod 2 = 0">1</xsl:if>
  </xsl:template>
</xsl:stylesheet>

عندما يطبق على هذا المصدر مستند XML:

<nums>
  <num>01</num>
  <num>02</num>
  <num>03</num>
  <num>04</num>
  <num>05</num>
  <num>06</num>
  <num>07</num>
  <num>08</num>
  <num>09</num>
  <num>10</num>
</nums>

ينتج المطلوب (تصفية) النتيجة التي تحتوي فقط على العقد حتى مع القيم:

Filtering by IsEven:
<num>02</num>
<num>04</num>
<num>06</num>
<num>08</num>
<num>10</num>

المزيد من المعلومات حول البرمجة الوظيفية في XSLT ويمكن الاطلاع على صفحة FXSL و المكتبة نفسها يمكن تحميلها من sourceforce المشروع.

العودة إلى الخرسانة المشكلة:

هذا التحول:

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:f="http://fxsl.sf.net/"
xmlns:myFilter="myFilter"
>

  <xsl:import href="filter.xsl"/>

  <!-- To be applied on Orders.xml -->

  <xsl:output indent="yes" omit-xml-declaration="yes"/>

  <myFilter:myFilter/>

  <xsl:template match="/">
    <xsl:variable name="vFilter"
         select="document('')/*/myFilter:*[1]"/>

    Filtering by PRICE < 15:
    <xsl:call-template name="_filter">
        <xsl:with-param name="pList" select="/*/*"/>
        <xsl:with-param name="pController" select="$vFilter"/>
    </xsl:call-template>

  </xsl:template>

  <xsl:template name="myFilter" mode="f:FXSL"
    match="myFilter:*">
    <xsl:param name="arg1"/>

    <xsl:if test="$arg1/PRICE &lt; 15">1</xsl:if>
  </xsl:template>
</xsl:stylesheet>

عندما يطبق على هذا المصدر مستند XML:

<ORDERS>
  <ORDER>
    <PRICE>10</PRICE>
  </ORDER>
  <ORDER>
    <PRICE>7</PRICE>
  </ORDER>
  <ORDER>
      <PRICE>22</PRICE>
</ORDER>
  <ORDER>
      <PRICE>16</PRICE>
  </ORDER>
  <ORDER>
      <PRICE>13</PRICE>
  </ORDER>
  <ORDER>
      <PRICE>19</PRICE>
  </ORDER>
</ORDERS>  

تنتج يريد النتيجة:

Filtering by PRICE < 15:
<ORDER>
   <PRICE>10</PRICE>
</ORDER>
<ORDER>
   <PRICE>7</PRICE>
</ORDER>
<ORDER>
   <PRICE>13</PRICE>
</ORDER>

استخدم المكتبة EXSLT، وتحديدا داين: تقييم وظيفة، والتي يمكن تقييم سلسلة بمثابة تعبير XPath.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top