-
Notifications
You must be signed in to change notification settings - Fork 0
/
day8-2.p
95 lines (71 loc) · 3.85 KB
/
day8-2.p
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
/*
--- Day 8: Memory Maneuver ---
--- Part Two ---
The second check is slightly more complicated: you need to find the value of the root node (A in the example above).
The value of a node depends on whether it has child nodes.
If a node has no child nodes, its value is the sum of its metadata entries. So, the value of node B is 10+11+12=33, and the value of node D is 99.
However, if a node does have child nodes, the metadata entries become indexes which refer to those child nodes. A metadata entry of 1 refers to the first child node, 2 to the second, 3 to the third, and so on. The value of this node is the sum of the values of the child nodes referenced by the metadata entries. If a referenced child node does not exist, that reference is skipped. A child node can be referenced multiple time and counts each time it is referenced. A metadata entry of 0 does not refer to any child node.
For example, again using the above nodes:
Node C has one metadata entry, 2. Because node C has only one child node, 2 references a child node which does not exist, and so the value of node C is 0.
Node A has three metadata entries: 1, 1, and 2. The 1 references node A's first child node, B, and the 2 references node A's second child node, C. Because node B has a value of 33 and node C has a value of 0, the value of node A is 33+33+0=66.
So, in this example, the value of the root node is 66.
What is the value of the root node?
*/
DEFINE VARIABLE iData AS INTEGER NO-UNDO.
DEFINE VARIABLE iNodeSeq AS INTEGER NO-UNDO.
DEFINE VARIABLE iPos AS INTEGER INITIAL 1 NO-UNDO.
DEFINE VARIABLE lcData AS LONGCHAR NO-UNDO.
DEFINE TEMP-TABLE ttNode NO-UNDO
FIELD iNodeId AS INTEGER
FIELD iNodeValue AS INTEGER
INDEX ix IS PRIMARY UNIQUE iNodeId.
DEFINE TEMP-TABLE ttTree NO-UNDO
FIELD iFatherId AS INTEGER
FIELD iChildId AS INTEGER
FIELD iChildNum AS INTEGER
INDEX ix IS PRIMARY UNIQUE iFatherId iChildNum.
ETIME(YES).
COPY-LOB FILE "C:\User\JCCARDOT\Perso\Travail\aoc\aoc2018\day8.txt" TO lcData.
lcData = REPLACE(REPLACE(lcData, CHR(10), ""), CHR(13), "").
FUNCTION computeNodeValue RETURNS INTEGER ( INPUT-OUTPUT piPos AS INTEGER, INPUT piNodeId AS INTEGER ):
DEFINE VARIABLE i AS INTEGER NO-UNDO.
DEFINE VARIABLE iChildNum AS INTEGER NO-UNDO.
DEFINE VARIABLE iChilds AS INTEGER NO-UNDO.
DEFINE VARIABLE iMetas AS INTEGER NO-UNDO.
DEFINE VARIABLE iMetaSum AS INTEGER NO-UNDO.
DEFINE BUFFER ttTree FOR ttTree.
DEFINE BUFFER ttNode FOR ttNode.
ASSIGN
iChilds = INTEGER(ENTRY(piPos, lcData, " "))
iMetas = INTEGER(ENTRY(piPos + 1, lcData, " "))
piPos = piPos + 2.
IF iChilds > 0 THEN DO i = 1 TO iChilds:
iNodeSeq = iNodeSeq + 1.
CREATE ttNode.
ASSIGN ttNode.iNodeId = iNodeSeq
ttNode.iNodeValue = ttNode.iNodeValue + computeNodeValue(INPUT-OUTPUT piPos, ttNode.iNodeId).
CREATE ttTree.
ASSIGN ttTree.iFatherId = piNodeId
ttTree.iChildNum = i
ttTree.iChildId = ttNode.iNodeId.
END.
IF iMetas > 0 THEN DO:
IF iChilds = 0 THEN DO i = 0 TO iMetas - 1:
iMetaSum = iMetaSum + INTEGER(ENTRY(piPos + i, lcData, " ")).
END.
ELSE DO i = 0 TO iMetas - 1:
iChildNum = INTEGER(ENTRY(piPos + i, lcData, " ")).
FOR FIRST ttTree WHERE ttTree.iFatherId = piNodeId AND ttTree.iChildNum = iChildNum
,FIRST ttNode WHERE ttNode.iNodeId = ttTree.iChildId:
iMetaSum = iMetaSum + ttNode.iNodeValue.
END.
END.
piPos = piPos + iMetas.
END.
RETURN iMetaSum.
END FUNCTION.
MESSAGE ETIME SKIP
computeNodeValue(INPUT-OUTPUT iPos, 0)
VIEW-AS ALERT-BOX INFO BUTTONS OK.
/* 3 */
/* 32850 */