Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/google-sheets/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql 路径枚举模型,如何获得上级?_Sql_Sql Server 2008 - Fatal编程技术网

Sql 路径枚举模型,如何获得上级?

Sql 路径枚举模型,如何获得上级?,sql,sql-server-2008,Sql,Sql Server 2008,考虑下表数据: emp_name VARCHAR(25), path VARCHAR(150) Albert /Albert John /Albert/John Chuck /Albert/Chuck Tom /Albert/John/Tom Frank /Frank 我想得到汤姆的上司名单: John Albert (可以包括汤

考虑下表数据:

emp_name VARCHAR(25), path VARCHAR(150)
Albert                /Albert
John                  /Albert/John
Chuck                 /Albert/Chuck
Tom                   /Albert/John/Tom
Frank                 /Frank
我想得到汤姆的上司名单:

John
Albert
(可以包括汤姆)

是否可以在不拆分路径的情况下使用序列表(我找到的唯一方法)


DB is Sql server 2008 R2

您可以使用递归CTE拆分层次结构字符串值

declare @T table 
(
  ID int identity,
  emp_name varchar(25),
  [path] varchar(150)
)

insert into @T values
('Albert', 'Albert'),
('John',   'Albert/John'),
('Chuck',  'Albert/Chuck'),
('Tom',    'Albert/John/Tom'),
('Frank',  'Frank')

declare @EmpName varchar(25) = 'Tom'

;with cte(Sort, P1, P2, [path]) as
(
  select 1,
         1,
         charindex('/', [path]+'/', 1),
         [path]
  from @T
  where emp_name = @EmpName  
  union all
  select Sort+1,
         P2+1,
         charindex('/', [path]+'/', C.P2+1),
         [path]
  from cte as C
  where charindex('/', [path]+'/', C.P2+1) > 0
)
select substring([path], P1, P2-P1)
from cte
order by Sort
结果:

(No column name)
Albert
John
Tom
在此处测试查询:

还有一件事你可以试试

select T2.emp_name
from @T as T1
  inner join @T as T2
    on '/'+T1.[path]+'/' like '%/'+T2.emp_name+'/%' and
       T2.emp_name <> @EmpName  
where T1.emp_name = @EmpName
选择T2.emp\u名称
从@T到T1
内部连接@T as T2
在“/”+T1.[path]+'/'上,如“%/”+T2.emp_name++“/%”和
T2.emp_name@EmpName
其中T1.emp_name=@EmpName

您可以使用递归CTE拆分层次结构字符串值

declare @T table 
(
  ID int identity,
  emp_name varchar(25),
  [path] varchar(150)
)

insert into @T values
('Albert', 'Albert'),
('John',   'Albert/John'),
('Chuck',  'Albert/Chuck'),
('Tom',    'Albert/John/Tom'),
('Frank',  'Frank')

declare @EmpName varchar(25) = 'Tom'

;with cte(Sort, P1, P2, [path]) as
(
  select 1,
         1,
         charindex('/', [path]+'/', 1),
         [path]
  from @T
  where emp_name = @EmpName  
  union all
  select Sort+1,
         P2+1,
         charindex('/', [path]+'/', C.P2+1),
         [path]
  from cte as C
  where charindex('/', [path]+'/', C.P2+1) > 0
)
select substring([path], P1, P2-P1)
from cte
order by Sort
结果:

(No column name)
Albert
John
Tom
在此处测试查询:

还有一件事你可以试试

select T2.emp_name
from @T as T1
  inner join @T as T2
    on '/'+T1.[path]+'/' like '%/'+T2.emp_name+'/%' and
       T2.emp_name <> @EmpName  
where T1.emp_name = @EmpName
选择T2.emp\u名称
从@T到T1
内部连接@T as T2
在“/”+T1.[path]+'/'上,如“%/”+T2.emp_name++“/%”和
T2.emp_name@EmpName
其中T1.emp_name=@EmpName

不使用递归方法是否可以执行此操作?@user-当然可以。正如您所说的,使用序列表。为什么不想使用递归CTE?它是否存在性能问题?您还可以使用字符串拆分函数。这里有一个包是在某某发布的。某某在哪里(链接)?我试图只使用序列表来完成它,但没有弄清楚。@user-不使用递归方法也可以完成吗?@user-当然可以。正如您所说的,使用序列表。为什么不想使用递归CTE?它是否存在性能问题?您还可以使用字符串拆分函数。这里有一个包是在某某发布的。某某在哪里(链接)?我试图只使用序列表来完成它,但无法找到它。@user-