/home/toolbox/public_html/solutions/1/101/a.c
1 #include <stdio.h>
2 #include <string.h>
3 #include <sys/types.h>
4 #include <sys/stat.h>
5 #include <fcntl.h>
6 #include <stdint.h>
7 #include <math.h>
8 #include <stdlib.h>
9
10 #define TRUE (1 == 1)
11 #define FALSE (1 != 1)
12
13 #define DEBUG if (FALSE)
14
15 /*
16 * Author: Isaac Traxler
17 * Date: 2014-10-30
18 * Purpose: fun
19 * Problem: 101 - The Blocks Problem
20 */
21
22 #define MAX_LINE 256
23
24 #define MOVE 0
25 #define PILE 3
26 #define ONTO 1
27 #define OVER 2
28
29 /*
30 move onto 1 0 + 1
31 move over 2 0 + 2
32 pile onto 4 3 + 1
33 pile over 5 3 + 2
34 */
35
36 #define MAX_BLOCKS 30
37
38 typedef struct LOCATION_STRUCT
39 {
40 /* BEGIN LOCATION_STRUCT */
41 int pile;
42 int depth;
43 } /* END LOCATION_STRUCT */ LOCATION_STRUCT;
44
45 typedef struct PILE_STRUCT
46 {
47 /* BEGIN PILE_STRUCT */
48 int cnt;
49 int p[MAX_BLOCKS];
50 } /* END PILE_STRUCT */ PILE_STRUCT;
51
52 /*
53 * This template reads data until a terminating value is reached.
54 */
55
56 int moreToDo;
57 int size;
58 int cmd;
59 int a;
60 int b;
61 PILE_STRUCT blocks[MAX_BLOCKS];
62 char commands[4][5] = { "move", "onto", "over", "pile" };
63
64
65 void dump()
66 {
67 /* FUNCTION dump */
68 int i;
69 int j;
70
71 for (i=0; size>i; i++)
72 {
73 /* for each pile */
74 printf("%d:", i);
75 for (j=0; blocks[i].cnt>j; j++)
76 {
77 /* for each element in the pile */
78 printf(" %d", blocks[i].p[j]);
79 } /* for each element in the pile */
80 printf("\n");
81 } /* for each pile */
82 } /* FUNCTION dump */
83
84 int getInput()
85 {
86 /* FUNCTION getInput */
87 int moreToDO;
88 char t[10];
89 int c1;
90 int c2;
91
92 scanf(" %s ", t);
93 moreToDo = 'q' != t[0];
94 if (moreToDo)
95 {
96 /* got a command */
97 /* assume valid command, so first letter is m or p, and p is 3 greater tham m */
98 c1 = t[0] - 'm'; /* if m, c1 = 0, else c1 = 3 */
99 /* now get second part of comand and 2 values */
100 scanf(" %d %s %d ", &a, t, &b);
101 if ('n' == t[1])
102 {
103 /* move */
104 c2 = ONTO;
105 } /* move */
106 else
107 {
108 /* pile */
109 c2 = OVER;
110 } /* pile */
111 cmd = c1 + c2;
112 DEBUG printf("%s %d %s %d -- %d\n", commands[c1], a, commands[c2], b, cmd);
113 } /* got a command */
114 return moreToDo;
115 } /* FUNCTION getInput */
116
117 void init()
118 {
119 /* FUNCTION init */
120 int i;
121
122 scanf(" %d ", &size);
123 for (i=0; i<size; i++)
124 {
125 /* for each i */
126 blocks[i].cnt = 1;
127 blocks[i].p[0] = i;
128 } /* for each i */
129 } /* FUNCTION init */
130
131 LOCATION_STRUCT fnd(int f)
132 {
133 /* FUNCTION fnd */
134 LOCATION_STRUCT toReturn;
135 int p;
136 int i;
137
138 toReturn.pile = -1; /* not found */
139 for (p=0; size>p; p++)
140 {
141 /* try each pile */
142 for (i=0; blocks[p].cnt>i; i++)
143 {
144 /* each item in this pile */
145 if (f == blocks[p].p[i])
146 {
147 /* found the desired block */
148 toReturn.pile = p;
149 toReturn.depth = i;
150 i = size;
151 p = size;
152 } /* found the desired block */
153 } /* each item in this pile */
154 } /* try each pile */
155 return toReturn;
156 } /* FUNCTION fnd */
157
158 void putOnTopOfPile(int x, int ple)
159 {
160 /* FUNCTION putOnTopOfPile */
161 DEBUG printf("pile = %d cnt = %d\n", ple, blocks[ple].cnt);
162 blocks[ple].p[blocks[ple].cnt] = x;
163 blocks[ple].cnt++;
164 } /* FUNCTION putOnTopOfPile */
165
166 void removeFromTopOfPile(int ple)
167 {
168 /* FUNCTION removeFromTopOfPile */
169 blocks[ple].cnt--;
170 } /* FUNCTION removeFromTopOfPile */
171
172 void ClearPileAbovePoint(LOCATION_STRUCT x)
173 {
174 /* FUNCTION ClearPileAbovePoint */
175 int i;
176 int tmp;
177
178 for (i=x.depth+1; blocks[x.pile].cnt>i; i++)
179 {
180 /* get each value above indicated point */
181 tmp = blocks[x.pile].p[i];
182 putOnTopOfPile(tmp, tmp);
183 } /* get each value above indicated point */
184 blocks[x.pile].cnt = x.depth + 1;
185 } /* FUNCTION ClearPileAbovePoint */
186
187 void movePileAbovePoint(LOCATION_STRUCT x, int ple)
188 {
189 /* FUNCTION movePileAbovePoint */
190 int i;
191 int tmp;
192
193 for (i=x.depth; blocks[x.pile].cnt>i; i++)
194 {
195 /* get each value above indicated point */
196 tmp = blocks[x.pile].p[i];
197 putOnTopOfPile(tmp, ple);
198 } /* get each value above indicated point */
199 blocks[x.pile].cnt = x.depth;
200 } /* FUNCTION movePileAbovePoint */
201
202 void process()
203 {
204 /* FUNCTION process */
205 LOCATION_STRUCT pa;
206 LOCATION_STRUCT pb;
207
208 pa = fnd(a);
209 pb = fnd(b);
210 if (pa.pile != pb.pile)
211 {
212 /* only do somethingif piles are different */
213 switch (cmd)
214 {
215 /* switch */
216 case MOVE+OVER:
217 {
218 /* MOVER + OVER */
219 /*
220 * clear blocks above a
221 * clear a
222 * put a above b
223 */
224 ClearPileAbovePoint(pa); /* clears everything from above location */
225 removeFromTopOfPile(pa.pile); /* clears pa only -- which mustbe at top */
226 putOnTopOfPile(a, pb.pile); /* puts a on top of pb's pile */
227 break;
228 } /* MOVER + OVER */
229 case MOVE+ONTO:
230 {
231 /* MOVER + ONTO */
232 /*
233 * clear blocks above a
234 * clear a
235 * clear blocks above b
236 * put a above b
237 */
238 ClearPileAbovePoint(pa); /* clears everything from above location */
239 removeFromTopOfPile(pa.pile); /* clears pa only -- which mustbe at top */
240 ClearPileAbovePoint(pb);
241 putOnTopOfPile(a, pb.pile); /* puts a on top of pb's pile */
242 break;
243 } /* MOVER + ONTO */
244 case PILE+OVER:
245 {
246 /* PILE + OVER */
247 movePileAbovePoint(pa, pb.pile);
248 break;
249 } /* PILE + OVER */
250 case PILE+ONTO:
251 {
252 /* PILE + ONTO */
253 ClearPileAbovePoint(pb);
254 movePileAbovePoint(pa, pb.pile);
255 break;
256 } /* PILE + ONTO */
257 } /* switch */
258 } /* only do somethingif piles are different */
259 DEBUG dump();
260 } /* FUNCTION process */
261
262 int main ()
263 {
264 /* main */
265 int moreToDo;
266
267 init();
268 moreToDo = getInput();
269 DEBUG dump();
270 while (moreToDo)
271 {
272 /* while */
273 process();
274 moreToDo = getInput();
275 } /* while */
276 dump();
277 return EXIT_SUCCESS;
278 } /* main */
279