Jump to content

Recommended Posts

Posted

I have an XML similar structure like this

<People>	<Person>		<type>Male</type>		<vegetarian>False</vegetarian>	</Person>	<Person>		<type>Female</type>		<vegetarian>False</vegetarian>	</Person>	<Person>		<type>Female</type>		<vegetarian>True</vegetarian>	</Person>	<Person>		<type>Male</type>		<vegetarian>True</vegetarian>	</Person>	<Person>		<type>Male</type>		<vegetarian>False</vegetarian>	</Person>		<Person>		<type>Child</type>		<vegetarian>False</vegetarian>	</Person><People>

Now I want to group all types and count the variants. How many are vegetarian and how many are not. Then total amount of each types.I have manage to do the total counting and sorting between types but I don't know how to count types vegetarians and non-vegetarians for each type?Notice that in my XML there are more types which are unknown. So I cannot use hard coding for types.Output is something like this

<TABLE><TR>	<TD>Gender</TD>	<TD>Vetarian</TD>	<TD>Non-Vegetarian</TD>	<TD>Total</TD></TR><TR>	<TD>Male</TD>	<TD>1</TD>	<TD>2</TD>	<TD>3</TD></TR><TR>	<TD>Female</TD>	<TD>1</TD>	<TD>1</TD>	<TD>2</TD></TR><TR>	<TD>Child</TD>	<TD>0</TD>	<TD>1</TD>	<TD>1</TD></TR></TABLE>

Posted

And how exactly did you arranged the output in that table? I feel this might requre xsl:key which I'm not so experienced with, so showing how you did it might give me a good start.

Posted

you can create this table with this:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ><xsl:output method="html"/><xsl:template match="/">	<TABLE>	<TR>		<TD>Gender</TD>		<TD>vegetarian</TD>		<TD>Non-Vegetarian</TD>		<TD>Total</TD>	</TR>	<TR>		<TD>Male</TD>		<TD><xsl:value-of select="count(//Person[type='Male'][vegetarian='True'])" /></TD>		<TD><xsl:value-of select="count(//Person[type='Male'][vegetarian='False'])" /></TD>		<TD><xsl:value-of select="count(//Person[type='Male'])" /></TD>	</TR>	<TR>		<TD>Female</TD>		<TD><xsl:value-of select="count(//Person[type='Female'][vegetarian='True'])" /></TD>		<TD><xsl:value-of select="count(//Person[type='Female'][vegetarian='False'])" /></TD>		<TD><xsl:value-of select="count(//Person[type='Female'])" /></TD>	</TR>	<TR>		<TD>Child</TD>		<TD><xsl:value-of select="count(//Person[type='Child'][vegetarian='True'])" /></TD>		<TD><xsl:value-of select="count(//Person[type='Child'][vegetarian='False'])" /></TD>		<TD><xsl:value-of select="count(//Person[type='Child'])" /></TD>	</TR>	</TABLE></xsl:template></xsl:stylesheet>

If your requirements are more elaborate, than you will need to be more specific

Posted

Just of curiosity. Scince when does "Child" count as a "gender" (hah.. I didn't noticed earlier)?Well, you said yourself that theese aren't the only types, right? Now that aalbetski gave me a good start, I think I could offer you THE solution:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" ><xsl:output method="html"/><xsl:template match="/">	<TABLE>	<TR>		<TD>Gender</TD>		<TD>vegetarian</TD>		<TD>Non-Vegetarian</TD>		<TD>Total</TD>	</TR>	<xsl:for-each slect="//type">		<TR>			<TD><xsl:value-of select="."/></TD>			<TD><xsl:value-of select="count(../Person[type=. and vegetarian='True'])" /></TD>			<TD><xsl:value-of select="count(../Person[type=. and vegetarian='False'])" /></TD>			<TD><xsl:value-of select="count(../Person[type=.])" /></TD>		</TR>	</xsl:for-each>	</TABLE></xsl:template></xsl:stylesheet>

Posted

In case you are interested, the following uses the 'Muenchian' method of selecting unique values. It does utilize keys and may be of interest just as another way to do the same thing

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"  version="1.0"><xsl:output method="html"/><xsl:key name="Gender"  match="Person" use="type"/><xsl:template match="/"><table border="1">	<tr>		<td>Gender</td>		<td>Vegetarian</td>		<td>Non-Vegetarian</td>		<td>Total</td>	</tr>	<xsl:for-each select="//Person[count(. | key('Gender', type)[1]) = 1]/type">		<xsl:variable name="gender" select="."/>		<tr>			<td><xsl:value-of select="$gender"/></td>			<td><xsl:value-of select="count(//Person[type=$gender][vegetarian='True'])"/></td>			<td><xsl:value-of select="count(//Person[type=$gender][vegetarian='False'])"/></td>			<td><xsl:value-of select="count(//Person[type=$gender])"/></td>		</tr>	</xsl:for-each></table></xsl:template></xsl:stylesheet>

Posted

Thank you for your answers! I managed to solve my problem with the last aalbetski's sollution. Since I'm still relative new to xml/xsl (etc.) issues I had more complex sollution before these ones. Again it seems that the simpliest ones are the best ones as well. I have still something here to digest but any way I can now do what I wanted. Thanks again.And you were right boen_robot. Child is not a gender but I tried to create something similar to my code and I guess this was the bad addition to my example:) I just tried to add more variants to my example to emphasize the importance of the issue that the type is unknown and can vary.

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...