Skip to content

Commit 3c67665

Browse files
authored
circular-buffer: Add canonical data (#488)
* circular-buffer: Add canonical data The circular-buffer exercise was first added in 2014 May at #9, with Ruby and Javascript as the initial implementing tracks: * exercism/DEPRECATED.javascript#17 * exercism/ruby#17 Implementing tracks: * https://github.com/exercism/xcsharp/blob/master/exercises/circular-buffer/CircularBufferTest.cs * https://github.com/exercism/xdlang/blob/master/exercises/circular-buffer/circular_buffer.d * https://github.com/exercism/xecmascript/blob/master/exercises/circular-buffer/circular-buffer.spec.js * https://github.com/exercism/xerlang/blob/master/exercises/circular-buffer/circular_buffer_tests.erl * https://github.com/exercism/xfsharp/blob/master/exercises/circular-buffer/CircularBufferTest.fs * https://github.com/exercism/xgo/blob/master/exercises/circular-buffer/circular_buffer_test.go * https://github.com/exercism/xjavascript/blob/master/exercises/circular-buffer/circular-buffer.spec.js * https://github.com/exercism/xlfe/blob/master/exercises/circular-buffer/test/circular-buffer-tests.lfe * https://github.com/exercism/xlua/blob/master/exercises/circular-buffer/circular-buffer_spec.lua * https://github.com/exercism/xpascal/blob/master/exercises/circular-buffer/uCircularBufferTests.pas * https://github.com/exercism/xpython/blob/master/exercises/circular-buffer/circular_buffer_test.py * https://github.com/exercism/xruby/blob/master/exercises/circular-buffer/circular_buffer_test.rb * https://github.com/exercism/xrust/blob/master/exercises/circular-buffer/tests/circular-buffer.rs All tracks pretty much implement the same tests, except: * Tracks typically have the "read item just written" and "each item can only be read once" tests combined. These tests split the two. * In dynamically-typed languages, buffers may be able to store heterogeneous types. This concept is not expressed in these tests. * In some statically-typed languages, buffers use generics, such that buffers may store any one type of the client's choosing. This concept is also not expressed in these tests. * The final test (ensuring that overwrite drops the right items) was more complex: capacity 5, 3 writes, 2 reads, write, read, 4 writes, 2 overwrites, 5 reads. It's been simplified to capacity 3, 3 writes, 1 read, write, overwrite, 3 reads. Closes https://github.com/exercism/todo/issues/79
1 parent c96351a commit 3c67665

File tree

1 file changed

+343
-0
lines changed

1 file changed

+343
-0
lines changed
Lines changed: 343 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,343 @@
1+
{
2+
"#": [
3+
"In general, these circular buffers are expected to be stateful,",
4+
"and each language will operate on them differently.",
5+
"Tests tend to perform a series of operations, some of which expect a certain result.",
6+
"As such, this common test suite can only say in abstract terms what should be done.",
7+
"",
8+
"Tests will contain a number of operations. The operation will be specified in the `operation` key.",
9+
"Based on the operation, other keys may be present.",
10+
"read: Reading from the buffer should succeed if and only if `should_succeed` is true.",
11+
" If it should succeed, it should produce the item at `expected`. ",
12+
" If it should fail, `expected` will not be present. ",
13+
"write: Writing the item located at `item` should succeed if and only if `should_succeed` is true.",
14+
"overwrite: Write the item located at `item` into the buffer, removing the oldest item if necessary.",
15+
"clear: Clear the buffer.",
16+
"",
17+
"Failure of either `read` or `write` may be indicated in a manner appropriate for your language:",
18+
"Raising an exception, returning (int, error), returning Option<int>, etc.",
19+
"",
20+
"Finally, note that all values are integers.",
21+
"If your language contains generics, you may consider allowing buffers to contain other types.",
22+
"Tests for that are not included here.",
23+
""
24+
],
25+
"cases": [
26+
{
27+
"description": "reading empty buffer should fail",
28+
"capacity": 1,
29+
"operations": [
30+
{
31+
"operation": "read",
32+
"should_succeed": false
33+
}
34+
]
35+
},
36+
{
37+
"description": "can read an item just written",
38+
"capacity": 1,
39+
"operations": [
40+
{
41+
"operation": "write",
42+
"item": 1,
43+
"should_succeed": true
44+
},
45+
{
46+
"operation": "read",
47+
"should_succeed": true,
48+
"expected": 1
49+
}
50+
]
51+
},
52+
{
53+
"description": "each item may only be read once",
54+
"capacity": 1,
55+
"operations": [
56+
{
57+
"operation": "write",
58+
"item": 1,
59+
"should_succeed": true
60+
},
61+
{
62+
"operation": "read",
63+
"should_succeed": true,
64+
"expected": 1
65+
},
66+
{
67+
"operation": "read",
68+
"should_succeed": false
69+
}
70+
]
71+
},
72+
{
73+
"description": "items are read in the order they are written",
74+
"capacity": 2,
75+
"operations": [
76+
{
77+
"operation": "write",
78+
"item": 1,
79+
"should_succeed": true
80+
},
81+
{
82+
"operation": "write",
83+
"item": 2,
84+
"should_succeed": true
85+
},
86+
{
87+
"operation": "read",
88+
"should_succeed": true,
89+
"expected": 1
90+
},
91+
{
92+
"operation": "read",
93+
"should_succeed": true,
94+
"expected": 2
95+
}
96+
]
97+
},
98+
{
99+
"description": "full buffer can't be written to",
100+
"capacity": 1,
101+
"operations": [
102+
{
103+
"operation": "write",
104+
"item": 1,
105+
"should_succeed": true
106+
},
107+
{
108+
"operation": "write",
109+
"item": 2,
110+
"should_succeed": false
111+
}
112+
]
113+
},
114+
{
115+
"description": "a read frees up capacity for another write",
116+
"capacity": 1,
117+
"operations": [
118+
{
119+
"operation": "write",
120+
"item": 1,
121+
"should_succeed": true
122+
},
123+
{
124+
"operation": "read",
125+
"should_succeed": true,
126+
"expected": 1
127+
},
128+
{
129+
"operation": "write",
130+
"item": 2,
131+
"should_succeed": true
132+
},
133+
{
134+
"operation": "read",
135+
"should_succeed": true,
136+
"expected": 2
137+
}
138+
]
139+
},
140+
{
141+
"description": "read position is maintained even across multiple writes",
142+
"capacity": 3,
143+
"operations": [
144+
{
145+
"operation": "write",
146+
"item": 1,
147+
"should_succeed": true
148+
},
149+
{
150+
"operation": "write",
151+
"item": 2,
152+
"should_succeed": true
153+
},
154+
{
155+
"operation": "read",
156+
"should_succeed": true,
157+
"expected": 1
158+
},
159+
{
160+
"operation": "write",
161+
"item": 3,
162+
"should_succeed": true
163+
},
164+
{
165+
"operation": "read",
166+
"should_succeed": true,
167+
"expected": 2
168+
},
169+
{
170+
"operation": "read",
171+
"should_succeed": true,
172+
"expected": 3
173+
}
174+
]
175+
},
176+
{
177+
"description": "items cleared out of buffer can't be read",
178+
"capacity": 1,
179+
"operations": [
180+
{
181+
"operation": "write",
182+
"item": 1,
183+
"should_succeed": true
184+
},
185+
{
186+
"operation": "clear"
187+
},
188+
{
189+
"operation": "read",
190+
"should_succeed": false
191+
}
192+
]
193+
},
194+
{
195+
"description": "clear frees up capacity for another write",
196+
"capacity": 1,
197+
"operations": [
198+
{
199+
"operation": "write",
200+
"item": 1,
201+
"should_succeed": true
202+
},
203+
{
204+
"operation": "clear"
205+
},
206+
{
207+
"operation": "write",
208+
"item": 2,
209+
"should_succeed": true
210+
},
211+
{
212+
"operation": "read",
213+
"should_succeed": true,
214+
"expected": 2
215+
}
216+
]
217+
},
218+
{
219+
"description": "clear does nothing on empty buffer",
220+
"capacity": 1,
221+
"operations": [
222+
{
223+
"operation": "clear"
224+
},
225+
{
226+
"operation": "write",
227+
"item": 1,
228+
"should_succeed": true
229+
},
230+
{
231+
"operation": "read",
232+
"should_succeed": true,
233+
"expected": 1
234+
}
235+
]
236+
},
237+
{
238+
"description": "overwrite acts like write on non-full buffer",
239+
"capacity": 2,
240+
"operations": [
241+
{
242+
"operation": "write",
243+
"item": 1,
244+
"should_succeed": true
245+
},
246+
{
247+
"operation": "overwrite",
248+
"item": 2
249+
},
250+
{
251+
"operation": "read",
252+
"should_succeed": true,
253+
"expected": 1
254+
},
255+
{
256+
"operation": "read",
257+
"should_succeed": true,
258+
"expected": 2
259+
}
260+
]
261+
},
262+
{
263+
"description": "overwrite removes the oldest item on full buffer",
264+
"capacity": 2,
265+
"operations": [
266+
{
267+
"operation": "write",
268+
"item": 1,
269+
"should_succeed": true
270+
},
271+
{
272+
"operation": "write",
273+
"item": 2,
274+
"should_succeed": true
275+
},
276+
{
277+
"operation": "overwrite",
278+
"item": 3
279+
},
280+
{
281+
"operation": "read",
282+
"should_succeed": true,
283+
"expected": 2
284+
},
285+
{
286+
"operation": "read",
287+
"should_succeed": true,
288+
"expected": 3
289+
}
290+
]
291+
},
292+
{
293+
"description": "overwrite doesn't remove an already-read item",
294+
"capacity": 3,
295+
"operations": [
296+
{
297+
"operation": "write",
298+
"item": 1,
299+
"should_succeed": true
300+
},
301+
{
302+
"operation": "write",
303+
"item": 2,
304+
"should_succeed": true
305+
},
306+
{
307+
"operation": "write",
308+
"item": 3,
309+
"should_succeed": true
310+
},
311+
{
312+
"operation": "read",
313+
"should_succeed": true,
314+
"expected": 1
315+
},
316+
{
317+
"operation": "write",
318+
"item": 4,
319+
"should_succeed": true
320+
},
321+
{
322+
"operation": "overwrite",
323+
"item": 5
324+
},
325+
{
326+
"operation": "read",
327+
"should_succeed": true,
328+
"expected": 3
329+
},
330+
{
331+
"operation": "read",
332+
"should_succeed": true,
333+
"expected": 4
334+
},
335+
{
336+
"operation": "read",
337+
"should_succeed": true,
338+
"expected": 5
339+
}
340+
]
341+
}
342+
]
343+
}

0 commit comments

Comments
 (0)