正規表現によるマッチング機能が欲しいのですが、XPath 1.0 にはそのような機能がありません。
仕方なく自分で拡張することにし、ネットで検索したところ、良い記事がありました。
http://www.microsoft.com/china/MSDN/library/data/xml/AddingCustomFunctionstoXpath.mspx?mfr=true
この記事では分割と置換を定義していますが、一致するものはありません。
コードを注意深く観察した
結果、関数を拡張するのは非常に簡単で、次の段落を変更するだけであることがわかりました。
1: CustomContext.cs
// カスタム関数への参照を解決する関数。
public オーバーライド IXsltContextFunction ResolveFunction(文字列プレフィックス,
文字列名、XPathResultType[] ArgTypes)
{
XPathRegExtensionFunction 関数 = null;
// 適切な拡張関数クラスのインスタンスを作成します。
スイッチ(名前)
{
「一致」の場合:
//使用法
// myFunctions:Matches(string ソース, string Regex_pattern) はブール値を返します
func = new XPathRegExtensionFunction("一致", 2, 2, new
XPathResultType[] {XPathResultType.String, XPathResultType.String}
、XPathResultType.Boolean );
壊す;
「分割」の場合:
//使用法
// myFunctions:Split(string source, string Regex_pattern, int n) は文字列を返します
func = new XPathRegExtensionFunction("Split", 3, 3, new
XPathResultType[] {XPathResultType.String, XPathResultType.String,
XPathResultType.Number}、XPathResultType.String);
壊す;
「置換」の場合:
//使用法
// myFunctions:Replace(string source, string Regex_pattern, string replace_string) は文字列を返します
func = new XPathRegExtensionFunction("置換", 3, 3, new
XPathResultType[] {XPathResultType.String, XPathResultType.String,
XPathResultType.String}、XPathResultType.String);
壊す;
}
戻り関数;
}
2: XPathRegExtensionFunction.cs
// このメソッドは、ユーザー定義関数を実行するために実行時に呼び出されます。
public object Invoke(XsltContext xsltContext, object[] args,
XPathNavigator docContext)
{
正規表現 r;
文字列 str = null;
// 2 つのカスタム XPath 拡張関数
スイッチ(m_関数名)
{
「一致」の場合:
r = 新しい正規表現(args[1].ToString());
MatchCollection m = r.Matches(args[0].ToString());
if (m.Count == 0)
{
false を返します。
}
それ以外
{
true を返します。
}
ブレーク;
ケース「分割」:
r = 新しい正規表現(args[1].ToString());
string[] s1 = r.Split(args[0].ToString());
int n = Convert.ToInt32(args[2]);
if (s1.Length < n)
str = "";
それ以外
str = s1[n - 1];
壊す;
「置換」の場合:
r = 新しい正規表現(args[1].ToString());
文字列 s2 = r.Replace(args[0].ToString(), args[2].ToString());
str = s2;
壊す;
}
(オブジェクト)str;を返します。
}
もう 1 つのファイルである XPathExtensionVariable.cs は、実際には関数の拡張とは何の関係もありません。パラメータを設定するために使用されます。
これら 2 つのファイルを変更した後、次を呼び出すことができます。
query = navigator.Compile("xdUtil:Match(9,'\d')");
CustomContext cntxt = new CustomContext();
// myFunctions プレフィックスの名前空間定義を追加します。
cntxt.AddNamespace("xdUtil", " http://myXPathExtensionFunctions ");
query.SetContext(cntxt);
Evaluate(クエリ、ナビゲータ);
もちろん、XPath2.0 に対応していれば良いのですが、XPath2.0 のこれらの機能はすべて組み込みでサポートされていますが、残念ながらまだサポートされていないようです。
完全なコードはここにあります: