Как уже упоминалось @Kory Gill, вы пропустили некоторые ограничения для правильного определения вашего запроса (и они также не отображаются в вашем примере), например:
- The *Столбцы 1005 * и
ManagerId
не обязательно должны быть в порядке
(или менеджер выше в иерархии всегда указан первым?) - Нет никакой связи между
ManagerId
и уровень иерархии
(или менеджер выше в иерархии всегда ниже ManagerId
?) - Глубина иерархии не определена (неограничена)
(Полагаю, что после реорганизации число уровней менеджера всегда может возрасти)
Если предположить, что вышеуказанные ограничения применимы, вопрос становится более сложным, но и более сложным.Чтобы показать это, я установил для Id
топ-менеджера John Doe
значение 11
и соответственно отсортировал список, оставив исходную иерархию без изменений:
$Employees = ConvertFrom-Csv 'ID, FirstName, LastName, ManagerId
2, Jane, Doe, 11
11, John, Doe, 0
45, Josh, Davis, 11
33, Steve, Clark, 2'
Какие из этих требований вы могли быхочу создать рекурсивную функцию для определения менеджера менеджера (менеджера ... и т. д.).Ниже приведен пример того, как вы можете решить эту проблему:
Function Add-ManagerLevel([Object[]]$Employees) {
Function Get-Level($ManagerId, [Int]$Level = 0) { # 0 is the top of hierarchy
$Manager = $Employees | Where-Object {$_.Id -eq $ManagerId}
If (!$Manager) {$Level} Else {Get-Level $Manager.ManagerId ($Level + 1)}
}
$Employees | ForEach-Object {
$_ | Add-Member "Level" (Get-Level $_.ManagerId) -PassThru
}
}
обратите внимание, что функция справки Get-Level
вызывает себя, чтобы выяснить, есть ли у менеджера более высокий менеджер.
Это даст следующий вывод:
Add-ManagerLevel $Employees | Format-Table
ID FirstName LastName ManagerId Level
-- --------- -------- --------- -----
2 Jane Doe 11 1
11 John Doe 0 0
45 Josh Davis 11 1
33 Steve Clark 2 2
По какому результату вы можете отсортировать свой список на уровне иерархии, например:
Add-ManagerLevel $Employees | Sort-Object Level | Format-Table