现在,实体框架4中不支持包含HierarchyID的CLR UDT.HierarchyID.ToString()很有用,但是一旦任何项目有10个以上的兄弟节点就会分解(基本结构是 / 3 / 4/12 / 或 / 3/4/2 / 所以第12个节点将在第2个节点之前排序)。
关于潜在选择的更多信息:
将hierarchyID作为varbinary返回并实现我自己的二进制分类器
将hierarchyID作为varbinary返回并实现我自己的 hierarchyID.ToString()方法,该方法在构建字符串时用零填充数字,以便生成的字符串是可排序的(即“/ 0003” / 0004/0012 /“)。我反汇编了 Microsoft.SqlServer.Types.dll 并查看了实现。看起来Interals是基于一个名为“OrdTree”的类,我可以使用该类作为重新实现的基础。
为SQL编写我自己的CLR类型来处理二进制数据并构建自己的字符串(选项2的变体)。虽然,增加了部署头痛。
编写SQL udf来解析层次结构字符串并将其填充到数据库层。缺乏阵列处理/正则表达式似乎是最大的问题。
按数据库层的hierarchyID排序,并使用ROW_NUMBER()函数作为排序顺序的替代。
在.net图层上编写一些帮助方法,重新解析hierarchyId.ToString()并生成可排序的字符串(即“/ 0003/0004/0012 /”)。
所以我的问题是有人解决了这个限制吗?你有没有使用上述任何一种策略?如果是这样,怎么样?
答案 0 :(得分:4)
好吧,我似乎得到了观点,但没有回应。我有一些立即需要使用SQL上面的层次结构,所以我把一个静态助手类放在一起。我不认为这是一个完整的解决方案,但到目前为止它的工作相对较好。 PadPath
确实是这里的关键功能。
public static class SQLHierarchyManipulatin {
const int DEFAULT_PAD_LEN = 3;
const char DEFAULT_PAD_CHAR = '0';
public static string PadPath(string Hierarchy) {
return PadPath (Hierarchy, DEFAULT_PAD_LEN);
}
public static string PadPath(string Hierarchy, int padLen) {
string[] components = Hierarchy.Split('/');
for (var i = 0; i < components.Length; i++ ) {
if (components[i] != "") {
components[i] = components[i].PadLeft(padLen, DEFAULT_PAD_CHAR);
}
}
return string.Join("/", components);
}
public static int CurrentNodeIndex(string Hierarchy) {
string[] components = Hierarchy.Split('/');
string startItem = components[components.Length - 2]; //one slot back from trailing slash
return int.Parse(startItem);
}
public static string ParentPath (string Hierarchy) {
return Hierarchy.Substring(0, Hierarchy.TrimEnd('/').LastIndexOf('/') + 1);
}
public static string AppendChildWithPadding (string Hierarchy, int childIndex, int padLen) {
return AppendChild(Hierarchy, childIndex, DEFAULT_PAD_LEN);
}
public static string AppendChildWithPadding (string Hierarchy, int childIndex) {
return AppendChild(Hierarchy, childIndex, DEFAULT_PAD_LEN);
}
public static string AppendChild (string Hierarchy, int childIndex) {
return AppendChild(Hierarchy, childIndex, DEFAULT_PAD_LEN);
}
public static string AppendChild (string Hierarchy, int childIndex, int padLen) {
return Hierarchy + childIndex.ToString().PadLeft(padLen, DEFAULT_PAD_CHAR) + "/";
}
}
希望这有助于某人!虽然,我仍然希望听到人们的意见。