说,有一个扁平的顺序层次结构表,其特殊字符“+”表示层次结构级别
hr_table
ID FIELD1 My irrelevant comments
----------------
1 ASSETS No pluses - it means level0 hierarchy
2 +ASSETS_01 Level1 hierarchy
3 ++345667654 Level2 hierarchy
4 ++563255512 Level2 hierarchy
5 ...
有没有办法使用SQL在MSACCESS中创建字段结构?我正在尝试按如下方式构建最终数据:
final_data_table
ID LEVEL0 LEVEL1 LEVEL2 ...
-------------------------------------------
1 ASSETS ASSETS_01 345667654
2 ASSETS ASSETS_01 563255512
任何/所有帮助都非常感谢!
答案 0 :(得分:0)
好奇心让我变得更好,所以我探索了查询方法。我使用域聚合函数。请注意,域聚合函数可以使用大型数据集执行缓慢。但是,请考虑:
查询1:
SELECT hr_table.ID, IIf([Field1] Like "+*",Left([Field1],InStrRev([Field1],"+")),0) AS Prefix, IIf([Field1] Like "+*",Null,[Field1]) AS Asset1, IIf(InStrRev([Field1],"+")=1,Mid([Field1],2),Null) AS Asset2, IIf([Field1] Like "++*",Mid([Field1],InStrRev([Field1],"+")+1),Null) AS Data
FROM hr_table;
QUERY2:
SELECT Query1.ID, Query1.Prefix, DMax("Asset1","Query1","ID<=" & [ID]) AS A1, DMax("Asset2","Query1","ID<=" & [ID]) AS A2, Query1.Data
FROM Query1
WHERE ((Not (Query1.Data) Is Null));
QUERY3:
SELECT Query2.Prefix, Query2.A1, Query2.A2, Query2.Data, DCount("*","Query2","A1='" & [A1] & "' AND A2='" & [A2] & "' AND Prefix = '" & [Prefix] & "' AND ID<=" & [ID]) AS GrpSeq
FROM Query2;
Query4:
TRANSFORM Max(Query3.Data) AS MaxOfData
SELECT Query3.A1, Query3.A2, Query3.GrpSeq
FROM Query3
GROUP BY Query3.A1, Query3.A2, Query3.GrpSeq
PIVOT Query3.Prefix;
我绝对不确定Level3及以后的治疗方法。可能是VBA将是唯一的解决方法。
答案 1 :(得分:0)
以下代码已经过测试,可以使用您提到的数据结构。它目前设置为最多10个级别,但可以轻松更改。棘手的部分是在你拥有该ONE行的所有级别之前不写出记录(新行以不同的level1值开始,或者提供多个level-n值)。最后一行是在输入eof后写的。
Option Compare Database
Option Explicit
Function Parse_Fields()
Dim dbs As DAO.Database
Dim rsIN As DAO.recordSet
Dim rsOUT As DAO.recordSet
Dim i As Integer
Dim iPlus As Integer
Dim aLevels(10)
Dim bAdding As Boolean
Set dbs = CurrentDb
Set rsIN = dbs.OpenRecordset("hr_table")
Set rsOUT = dbs.OpenRecordset("final_data_table")
bAdding = False
Do While Not rsIN.EOF
'Debug.Print "Input: " & rsIN!field1
If left(rsIN!field1, 1) <> "+" Then
' Check if not first time thru... if not, write prior levels..
If bAdding = True Then
rsOUT.Update
End If
iPlus = 0
rsOUT.AddNew
rsOUT!Level0 = rsIN!field1
bAdding = True
' Don't issue the .Update yet! Wait until another Level0 or EOF.
Else
For iPlus = 1 To 10 ' Change code if more than ten levels
If Mid(rsIN!field1, iPlus, 1) <> "+" Then Exit For
Next iPlus
' Check if same level as previous! If so, do NOT overlay!
If Not IsNull(rsOUT.Fields(iPlus)) Then
For i = 1 To iPlus - 1 ' Save the proper levels for the new record.
aLevels(i) = rsOUT.Fields(i)
Next i
rsOUT.Update ' Need to write out record.
rsOUT.AddNew
For i = 1 To iPlus ' Populate the new record with prior levels
rsOUT.Fields(i) = aLevels(i)
Next i
rsOUT.Fields(iPlus) = Mid(rsIN!field1, iPlus) ' Add the new level
Else
rsOUT.Fields(iPlus) = Mid(rsIN!field1, iPlus)
End If
End If
rsIN.MoveNext ' Get next input
Loop
' Need to write out the final record we have beenbuilding!
rsOUT.Update
rsIN.Close
rsOUT.Close
Set rsIN = Nothing
Set rsOUT = Nothing
Set dbs = Nothing
Debug.Print "FINISHED!!"
End Function