powered by simpleCommunicator - 2.0.51     © 2025 Programmizd 02
Форумы / XML, XSL, XPath, XQuery [игнор отключен] [закрыт для гостей] / Помогите реализовать XSLT преобразование
6 сообщений из 6, страница 1 из 1
Помогите реализовать XSLT преобразование
    #37018248
Невир
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Добрый день!
Из XML ниже нужно получить статистику по общей сумме за регион для каждой валюты. Вывод названий регионов нужно получить в иерархической структуре.
Результат должен быть следующий:

Регион Северо-Западный
EUR = 4250
RUB = 1200
____Регион Выборгский
____EUR = 344585
____RUB = 515390430
____USD = 738942
________Регион тестовый
________EUR = 167710
________RUB = 423590850 // Обратите внимание, в этом регионе несколько сортировщиков и суммируется общая сумма отдельно для каждого номинала, соответственно
________USD = 732075

Пример XML
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
<Regions>
  <Region Id="3" Text="Северо-Западный">
    <Sorter Id="3" Text="Numeron #4266">
      <CCMinfo Cur="EUR" CurSum="4250"/>
      <CCMinfo Cur="RUB" CurSum="1200"/>
    </Sorter>
    <Region Id="4" Text="Выборгский">
      <Sorter Id="5" Text="Numeron #1436">
        <CCMinfo Cur="EUR" CurSum="344585"/>
        <CCMinfo Cur="RUB" CurSum="515390430"/>
        <CCMinfo Cur="USD" CurSum="738942"/>
      </Sorter>
      <Region Id="5" Text="Тестовый регион">
        <Sorter Id="2" Text="Numeron #5748">
          <CCMinfo Cur="EUR" CurSum="167710"/>
          <CCMinfo Cur="RUB" CurSum="423520300"/>
          <CCMinfo Cur="USD" CurSum="732075"/>
        </Sorter>
        <Sorter Id="1" Text="Numeron #7506">
          <CCMinfo Cur="RUB" CurSum="70550"/>
        </Sorter>
      </Region>
    </Region>
  </Region>
</Regions>

Вот как я пытаюсь решить это задачу
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0"
	xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt">
<xsl:decimal-format name="CBSMoney" decimal-separator="," grouping-separator=" "/>

<!--Этот шаблон выводит нужное количество пробелов. Используется перед выводом имени региона для отображения иерархии-->
  <xsl:template name="TabOutput">
    <xsl:param name="i" select="0"/>
    <xsl:param name="n"/>

    <xsl:if test="$n > $i">
       
      <xsl:call-template name="TabOutput">
        <xsl:with-param name="i" select="$i + 1"/>
        <xsl:with-param name="n" select="$n"/>
      </xsl:call-template>
    </xsl:if>
  </xsl:template>

<!--Шаблон для региона. Здесь вся работа происходит.-->
  <xsl:template match="Region">
    <xsl:param name="nesting" select="0"/>
    <xsl:param name="currentRegion" select="@Id"/>

<!--Выводим название региона-->
    <div style="text-align:left">
      <xsl:call-template name="TabOutput">
        <xsl:with-param name="n" select="$nesting * 4"/>
      </xsl:call-template>
      <span style="font-size:20;font-weight:bold">
        Регион <xsl:value-of select="@Text"/>
      </span>
    </div>
    <br/>

    <table style="text-align:center;border: 5px black;border-collapse: collapse;width:90%;">
      <tr>
        <th style="text-align: center;background: Silver;padding: 5px;border: 1px solid black;">Валюта</th>        
        <th style="text-align: center;background: Silver;padding: 5px;border: 1px solid black;">Сумма</th>
      </tr>

<!--Цикл по валютам сортировщиков внутри региона. Валюта повторяться не должна, должна суммироваться-->
      <xsl:for-each select="Sorter/CCMinfo[not(@Cur=preceding-sibling::CCMinfo/@Cur)]">
        <xsl:sort data-type="text" order="ascending" select="@Cur"/>
        <tr>
          <td style="text-align:center;background: White;padding: 5px;border: 1px solid black;">
            <xsl:value-of select="@Cur"/>pzd
          </td>          
          <td style="text-align:center;background: White;padding: 5px;border: 1px solid black;" nowrap="nowrap">
            <xsl:value-of select="format-number(sum(//Regions/Region[@Id = $currentRegion]/Sorter/CCMinfo[@Cur=$curCur]/@CurSum),'### ### ##0,00', 'CBSMoney')"/>
          </td>
        </tr>
      </xsl:for-each>
    </table>

<!--Рекурсивно применяем для каждого вложенного региона этот шаблон-->
    <xsl:apply-templates select="./Region">
      <xsl:with-param name="nesting" select="$nesting + 1"/>
    </xsl:apply-templates>
    <br/>

  </xsl:template>


  <xsl:template match="/">

      <xsl:apply-templates select="Regions/Region">
        <xsl:with-param name="nesting" select="0"/>
      </xsl:apply-templates>

  </xsl:template>
</xsl:stylesheet>
...
Рейтинг: 0 / 0
Помогите реализовать XSLT преобразование
    #37019386
refreg
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt" version="1.0">
	<xsl:decimal-format name="CBSMoney" decimal-separator="," grouping-separator=" "/>
	<xsl:key name="Sorter" match="//CCMinfo" use="@Cur"/>
	<!--Шаблон для региона. Здесь вся работа происходит.-->
	<xsl:template match="Region">
		<xsl:param name="nesting" select="0"/>
		<xsl:param name="currentRegion" select="@Id"/>
		<xsl:variable name="curRegion" select="."/>
		<!--Выводим название региона-->
		<div style="text-align:left; padding-left:{$nesting * 50}px">
			<span style="font-size:20;font-weight:bold">
				<xsl:text>Регион</xsl:text>
				<xsl:value-of select="@Text"/>
			</span>
			<br/>
			<table style="text-align:center;border: 5px black;border-collapse: collapse;width:90%;">
				<tr>
					<th style="text-align: center;background: Silver;padding: 5px;border: 1px solid black;">Валюта</th>
					<th style="text-align: center;background: Silver;padding: 5px;border: 1px solid black;">Сумма</th>
				</tr>
				<!--Цикл по валютам сортировщиков внутри региона. Валюта повторяться не должна, должна суммироваться-->
				<xsl:for-each select="Sorter/CCMinfo[generate-id()=generate-id(key('Sorter',@Cur)[../..=$curRegion])]">
					<xsl:sort data-type="text" order="ascending" select="@Cur"/>
					<tr>
						<td style="text-align:center;background: White;padding: 5px;border: 1px solid black;">
							<xsl:value-of select="@Cur"/>
							<xsl:text>pzd</xsl:text>
						</td>
						<td style="text-align:center;background: White;padding: 5px;border: 1px solid black;" nowrap="nowrap">
							<xsl:value-of select="format-number(sum(key('Sorter',@Cur)[../..=$curRegion]/@CurSum),'### ### ##0,00', 'CBSMoney')"/>
						</td>
					</tr>
				</xsl:for-each>
			</table>
		</div>
		<!--Рекурсивно применяем для каждого вложенного региона этот шаблон-->
		<xsl:apply-templates select="./Region">
			<xsl:with-param name="nesting" select="$nesting + 1"/>
		</xsl:apply-templates>
		<br/>
	</xsl:template>
	<!-- -->
	<xsl:template match="/">
		<xsl:apply-templates select="Regions/Region">
			<xsl:with-param name="nesting" select="0"/>
		</xsl:apply-templates>
	</xsl:template>
</xsl:stylesheet>
...
Рейтинг: 0 / 0
Помогите реализовать XSLT преобразование
    #37019994
Невир
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Спасибо за ответ!
Вот для такого xml, выводится сводная таблица по первому региону, а вот по вложенным почему-то нет.... И могли бы Вы идею изложить по решению, я находил информацию, но не смог разобраться.

Вот этот xml

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
<Regions>
  <Region Id="3" Text="Северо-Западный">
    <Sorter Id="4" Text="Numeron #3362">
      <CCMinfo Cur="EUR" CurSum="26365" />
      <CCMinfo Cur="RUB" CurSum="559574280"/>
      <CCMinfo Cur="USD" CurSum="614162"/>
    </Sorter>
    <Sorter Id="3" Text="Numeron #4266">
      <CCMinfo Cur="EUR" CurSum="4250"/>
      <CCMinfo Cur="RUB" CurSum="1200"/>
    </Sorter>
    <Region Id="4" Text="Выборгский">
      <Sorter Id="5" Text="Numeron #1436">
        <CCMinfo Cur="EUR" CurSum="344585"/>
        <CCMinfo Cur="RUB" CurSum="515390430"/>
        <CCMinfo Cur="USD" CurSum="738942"/>
      </Sorter>
      <Region Id="5" Text="1">
        <Sorter Id="2" Text="Numeron #5748">
          <CCMinfo Cur="EUR" CurSum="167710" />
          <CCMinfo Cur="RUB" CurSum="423520300"/>
          <CCMinfo Cur="USD" CurSum="732075"/>
        </Sorter>
        <Sorter Id="1" Text="Numeron #7506">
          <CCMinfo Cur="RUB" CurSum="70550"/>
        </Sorter>
      </Region>
    </Region>
  </Region>
</Regions>
...
Рейтинг: 0 / 0
Помогите реализовать XSLT преобразование
    #37020086
refreg
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НевирВот для такого xml, выводится сводная таблица по первому региону, а вот по вложенным почему-то нет.... Имхо, для всех регионов нормально... хотя я может не понял, зачем используется ID. Суммирование идет чисто по месту в структуре.
НевирИ могли бы Вы идею изложить по решению, я находил информацию, но не смог разобраться.Идея стандартная. Создаешь ключ по интересующим данным. А потом эти данные используешь (тут главное следить за контекстом). Остальное ты сам сделал. Конкретнее вопрос, в какой строке(подстроке) непонятно?
...
Рейтинг: 0 / 0
Помогите реализовать XSLT преобразование
    #37020264
Невир
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
И правда нормально, видимо я где-то ошибся в исходном xslt, он пообъемнее.
По поводу вопроса: объясни мне пожалуйста детально, как это работает.
Код: plaintext
1.
2.
<xsl:key name="Sorter" match="//CCMinfo" use="@Cur"/>
<xsl:for-each select="Sorter/CCMinfo[generate-id()=generate-id(key('Sorter',@Cur)[../..=$curRegion])]">.......</for-each>
...
Рейтинг: 0 / 0
Помогите реализовать XSLT преобразование
    #37020421
refreg
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Невир,

Попробуй разобраться с простым примером Группировка и сортировка годов . Если останутся вопросы, может вечером распишу. Да и по поиску в интернете полно информации. Ключевые слова "Группировка, уникальные значения"
...
Рейтинг: 0 / 0
6 сообщений из 6, страница 1 из 1
Форумы / XML, XSL, XPath, XQuery [игнор отключен] [закрыт для гостей] / Помогите реализовать XSLT преобразование
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]