Option Explicit
't07a_論理コード:継続行 _ を先頭に畳んで 1レコード=1論理文。
' CodeIDは読まない/TrimCodeHashは使う/診断表なし/完了メッセージあり。
' 実行順:CreateT07aTable → BuildLogicalCode
Public Sub CreateT07aTable()
Dim db As DAO.Database
Set db = CurrentDb
If TableExists07("t07a_論理コード") Then
MsgBox "t07a_論理コード は既に存在します。作成をスキップしました。", vbInformation
Exit Sub
End If
db.Execute "CREATE TABLE [t07a_論理コード] (" & _
"論理行ID LONG CONSTRAINT PK_t07a PRIMARY KEY, " & _
"プロシージャID LONG, " & _
"先頭コードラインID LONG, " & _
"末尾コードラインID LONG, " & _
"連結行数 LONG, " & _
"論理コード MEMO, " & _
"コメント行 YESNO, " & _
"空白行 YESNO, " & _
"シェイプ作成対象 YESNO, " & _
"シェイプ作成対象外 YESNO, " & _
"シェイプID LONG, " & _
"TrimCodeHash TEXT(16))", dbFailOnError
MsgBox "t07a_論理コード を作成しました。", vbInformation
End Sub
Public Sub BuildLogicalCode()
Dim db As DAO.Database
Set db = CurrentDb
If Not TableExists07("t07a_論理コード") Then
MsgBox "t07a_論理コード がありません。先に CreateT07aTable を実行してください。", vbCritical
Exit Sub
End If
db.Execute "DELETE FROM [t07a_論理コード]", dbFailOnError
Dim n As Long
n = DCount("*", "t01a_コード")
If n = 0 Then Exit Sub
Dim aP() As Long, aCid() As Long, aTC() As String
Dim aCmt() As Boolean, aBlk() As Boolean, aHash() As String
ReDim aP(1 To n): ReDim aCid(1 To n): ReDim aTC(1 To n)
ReDim aCmt(1 To n): ReDim aBlk(1 To n): ReDim aHash(1 To n)
Dim rsIn As DAO.Recordset
Set rsIn = db.OpenRecordset( _
"SELECT プロシージャID, コードラインID, TrimCode, コメント行, 空白行, TrimCodeHash " & _
"FROM [t01a_コード] ORDER BY プロシージャID, コードラインID", dbOpenSnapshot)
Dim i As Long
i = 0
Do While Not rsIn.EOF
i = i + 1
aP(i) = CLng(Nz(rsIn.Fields("プロシージャID").Value, 0))
aCid(i) = CLng(Nz(rsIn.Fields("コードラインID").Value, 0))
aTC(i) = CStr(Nz(rsIn.Fields("TrimCode").Value, ""))
aCmt(i) = (rsIn.Fields("コメント行").Value = True)
aBlk(i) = (rsIn.Fields("空白行").Value = True)
aHash(i) = CStr(Nz(rsIn.Fields("TrimCodeHash").Value, ""))
rsIn.MoveNext
Loop
rsIn.Close
Dim rsOut As DAO.Recordset
Set rsOut = db.OpenRecordset("SELECT * FROM [t07a_論理コード]", dbOpenDynaset)
Dim seq As Long: seq = 0
Dim k As Long: k = 1
Do While k <= n
Dim curProc As Long, headLine As Long
Dim headCmt As Boolean, headBlk As Boolean, headHash As String
Dim buf As String, cnt As Long, lastLine As Long
curProc = aP(k): headLine = aCid(k)
headCmt = aCmt(k): headBlk = aBlk(k): headHash = aHash(k)
buf = "": cnt = 0
Dim j As Long: j = k
Do
Dim seg As String, cont As Boolean
seg = aTC(j)
cont = IsContinuation(seg, aCmt(j))
If cont Then seg = DropTrailingUnderscore(seg)
If Len(buf) = 0 Then buf = seg Else buf = buf & " " & seg
cnt = cnt + 1
lastLine = aCid(j)
If cont And j < n Then
If aP(j + 1) = curProc Then j = j + 1 Else Exit Do
Else
Exit Do
End If
Loop
seq = seq + 1
rsOut.AddNew
rsOut.Fields("論理行ID").Value = seq
rsOut.Fields("プロシージャID").Value = curProc
rsOut.Fields("先頭コードラインID").Value = headLine
rsOut.Fields("末尾コードラインID").Value = lastLine
rsOut.Fields("連結行数").Value = cnt
rsOut.Fields("論理コード").Value = buf
rsOut.Fields("コメント行").Value = headCmt
rsOut.Fields("空白行").Value = headBlk
rsOut.Fields("シェイプ作成対象").Value = False
rsOut.Fields("シェイプ作成対象外").Value = False
rsOut.Fields("シェイプID").Value = Null
rsOut.Fields("TrimCodeHash").Value = headHash
rsOut.Update
k = j + 1
Loop
rsOut.Close
MsgBox "t07a_論理コード を作成しました。論理文 " & seq & " 件。", vbInformation
End Sub
Private Function IsContinuation(ByVal s As String, ByVal isCmt As Boolean) As Boolean
IsContinuation = False
If isCmt Then Exit Function
Dim t As String
t = RTrim$(s)
If Len(t) >= 2 Then
If Right$(t, 1) = "_" Then
Dim c As String
c = Mid$(t, Len(t) - 1, 1)
If c = " " Or c = vbTab Then IsContinuation = True
End If
End If
End Function
Private Function DropTrailingUnderscore(ByVal s As String) As String
Dim t As String
t = RTrim$(s)
If Right$(t, 1) = "_" Then t = Left$(t, Len(t) - 1)
DropTrailingUnderscore = RTrim$(t)
End Function
Private Function TableExists07(ByVal nm As String) As Boolean
Dim td As DAO.TableDef
On Error Resume Next
Set td = CurrentDb.TableDefs(nm)
TableExists07 = (Not td Is Nothing)
On Error GoTo 0
End Function