Вот решение VBA.В настоящее время требуется, чтобы вы преобразовали свою таблицу в официальную таблицу «Excel», что можно сделать, выделив таблицу данных, перейдя на ленту вставки и выбрав «Таблица».Преимущество этого в том, что этот код будет работать, даже если вы переместили таблицу на листе.
Я назвал свои столбцы «инициативой» и «этапом», и это актуально в строке 8 кода,Эти столбцы должны быть рядом друг с другом, чтобы этот код работал.Вам придется изменить его в соответствии с вашей ситуацией.Вы также можете изменить значение переменной startCell в строке 10.
Public Sub CreateInitiativeListForGnatt()
Dim tbl As ListObject 'The table object in your worksheet.
Dim projCols As Range 'The initiative and milestone columns in the table.
Dim projDict As Object 'The dictionary object we'll use to store key-values of initiative-[milestone1, milestone2, etc]
Dim startCell As Range
Set tbl = Worksheets("Sheet1").ListObjects("Table1")
Set projCols = Range(tbl & "[[initiative]:[milestone]]")
Set projDict = CreateObject("Scripting.Dictionary")
Set startCell = Worksheets("Sheet1").Range("D3") 'The first cell of the location where you want the list to be created.
For Each r In projCols.Rows
Call AddMilestoneToDictionary(projDict, r.Cells(1).Value, r.Cells(2).Value)
Next
Call writeInitiativeListToWorksheet(projDict, startCell)
End Sub
Private Sub AddMilestoneToDictionary(ByRef projDict, initiativeNumber As Variant, milestoneNumber As Variant)
If projDict.Exists(initiativeNumber) Then
projDict(initiativeNumber).Add milestoneNumber
Else
Set milestones = New Collection
milestones.Add (milestoneNumber)
projDict.Add initiativeNumber, milestones
End If
End Sub
Private Sub writeInitiativeListToWorksheet(ByVal projDict, startCell As Range)
Dim wrkSht As Worksheet
Dim currentRow As Integer, initCol As Integer, mileCol As Integer
Set wrkSht = startCell.Worksheet
currentRow = startCell.Row
initCol = startCell.Column
mileCol = startCell.Column + 1
For Each initiative In projDict.Keys
wrkSht.Cells(currentRow, initCol).Value = initiative
currentRow = currentRow + 1
For Each milestone In projDict(initiative)
wrkSht.Cells(currentRow, mileCol).Value = milestone
currentRow = currentRow + 1
Next
Next
End Sub