Hi Bjoern\Martin,
Thanks for the Pointers.
I wrote a sumfunction similar to that shown on MSDN. Here is the code in
case anyone finds it useful. No warranties gaurantees etc.
private class SumFunction : IXsltContextFunction
{
public const string Namespace = "CRO";
public const string FunctionName = "sum";
private System.Xml.XPath.XPathResultType[] m_argTypes =
new System.Xml.XPath.XPathResultType[] {
System.Xml.XPath.XPathResultType.Number};
#region IXsltContextFunction Members
public System.Xml.XPath.XPathResultType[] ArgTypes
{
get
{
return m_argTypes;
}
}
private double GetNumberFromInvokeArgument(object arg)
{
double dblValue = 0;
double dblOut = 0;
if (arg is XPathNodeIterator)
{
XPathNodeIterator i = (XPathNodeIterator)arg;
XPathNavigator navigator = i.Current;
while (i.MoveNext())
{
if(double.TryParse(i.Current.Value, out dblOut))
{
dblValue += dblOut;
}
else
{
throw new ArgumentException("sum() function
only supports number values");
}
}
}
else
{
throw new ArgumentException("sum() only supports node
path");
}
return dblValue;
}
public object Invoke(XsltContext xsltContext, object[] args,
System.Xml.XPath.XPathNavigator docContext)
{
if (args.Length == 0)
{
throw new ArgumentException("sum() needs at least one
argument ");
}
double argument1 = GetNumberFromInvokeArgument(args[0]);
return argument1;
}
public int Maxargs
{
get { return 1; }
}
public int Minargs
{
get { return 1; }
}
public System.Xml.XPath.XPathResultType ReturnType
{
get { return System.Xml.XPath.XPathResultType.Number; }
}
#endregion
}
Herer is the calling code
XPathExpression expr1 =
objNavigator.Compile("CRO:sum(//NOTALLCASHISSUEDDETAIL[NACIDSTANDARDCURRENCYID = $CurrencyId and NACIDSECURITYNAME = $SecurityName]/NACIDAMOUNTISSUED)");
XPathExpression expr2 =
objNavigator.Compile("CRO:sum(//ALLCASHISSUEDDETAIL[ACIDSTANDARDCURRENCYID =
$CurrencyId and ACIDSECURITYNAME = $SecurityName]/ACIDAMOUNTISSUED)");
CustomContext xsltContextAuthorisedShareClass = new
CustomContext((NameTable)objXML.NameTable);
xsltContextAuthorisedShareClass.AddParam("Security Name",
strShareClass);
xsltContextAuthorisedShareClass.AddParam("Currency Id",
strCurrencyID);
xsltContextAuthorisedShareClass.AddParam("ParValue ",
dblParValue.ToString());
xsltContextAuthorisedShareClass.AddNamespace("GCM" ,
"GCM");
expr1.SetContext(xsltContextAuthorisedShareClass);
expr2.SetContext(xsltContextAuthorisedShareClass);
dblAmt2 = (double)objNavigator.Evaluate(expr1);
dblAmt3 = (double)objNavigator.Evaluate(expr2);
Baz
"Bjoern Hoehrmann" wrote:
* Baz wrote in microsoft.public.dotnet.xml:
As the user can enter any characters options one and two would not suit.
Option 4 would get very inefficient if users entered multiple quotes so I am
going to look into option 3 though it may not be supported.
I don't think there is anything inefficient about #4. The expression
might become a little bit longer, but parsing it evaluating the concat
function is something a modern computer can do millions of times per
second. It seems http://support.microsoft.com/kb/324462 you can do #3
though.
--
Björn Höhrmann · mailto:bj****@hoehrmann.de · http://bjoern.hoehrmann.de
Weinh. Str. 22 · Telefon: +49(0)621/4309674 · http://www.bjoernsworld.de
68309 Mannheim · PGP Pub. KeyID: 0xA4357E78 · http://www.websitedev.de/