@@ -180,6 +180,99 @@ func BenchmarkContains100Unsafe(b *testing.B) {
180
180
benchContains (b , 100 , NewThreadUnsafeSet [int ]())
181
181
}
182
182
183
+ func benchContainsOne (b * testing.B , n int , s Set [int ]) {
184
+ nums := nrand (n )
185
+ for _ , v := range nums {
186
+ s .Add (v )
187
+ }
188
+
189
+ b .ResetTimer ()
190
+ for i := 0 ; i < b .N ; i ++ {
191
+ s .ContainsOne (- 1 )
192
+ }
193
+ }
194
+
195
+ func BenchmarkContainsOne1Safe (b * testing.B ) {
196
+ benchContainsOne (b , 1 , NewSet [int ]())
197
+ }
198
+
199
+ func BenchmarkContainsOne1Unsafe (b * testing.B ) {
200
+ benchContainsOne (b , 1 , NewThreadUnsafeSet [int ]())
201
+ }
202
+
203
+ func BenchmarkContainsOne10Safe (b * testing.B ) {
204
+ benchContainsOne (b , 10 , NewSet [int ]())
205
+ }
206
+
207
+ func BenchmarkContainsOne10Unsafe (b * testing.B ) {
208
+ benchContainsOne (b , 10 , NewThreadUnsafeSet [int ]())
209
+ }
210
+
211
+ func BenchmarkContainsOne100Safe (b * testing.B ) {
212
+ benchContainsOne (b , 100 , NewSet [int ]())
213
+ }
214
+
215
+ func BenchmarkContainsOne100Unsafe (b * testing.B ) {
216
+ benchContainsOne (b , 100 , NewThreadUnsafeSet [int ]())
217
+ }
218
+
219
+ // In this scenario, Contains argument escapes to the heap, while ContainsOne does not.
220
+ func benchContainsComparison (b * testing.B , n int , s Set [int ]) {
221
+ nums := nrand (n )
222
+ for _ , v := range nums {
223
+ s .Add (v )
224
+ }
225
+
226
+ b .Run ("Contains" , func (b * testing.B ) {
227
+ b .ReportAllocs ()
228
+ for i := 0 ; i < b .N ; i ++ {
229
+ for _ , v := range nums {
230
+ s .Contains (v ) // 1 allocation, v is moved to the heap
231
+ }
232
+ }
233
+ })
234
+ b .Run ("Contains slice" , func (b * testing.B ) {
235
+ b .ReportAllocs ()
236
+ for i := 0 ; i < b .N ; i ++ {
237
+ for i := range nums {
238
+ s .Contains (nums [i : i + 1 ]... ) // no allocations, using heap-allocated slice
239
+ }
240
+ }
241
+ })
242
+ b .Run ("ContainsOne" , func (b * testing.B ) {
243
+ b .ReportAllocs ()
244
+ for i := 0 ; i < b .N ; i ++ {
245
+ for _ , v := range nums {
246
+ s .ContainsOne (v ) // no allocations, using stack-allocated v
247
+ }
248
+ }
249
+ })
250
+ }
251
+
252
+ func BenchmarkContainsComparison1Unsafe (b * testing.B ) {
253
+ benchContainsComparison (b , 1 , NewThreadUnsafeSet [int ]())
254
+ }
255
+
256
+ func BenchmarkContainsComparison1Safe (b * testing.B ) {
257
+ benchContainsComparison (b , 1 , NewSet [int ]())
258
+ }
259
+
260
+ func BenchmarkContainsComparison10Unsafe (b * testing.B ) {
261
+ benchContainsComparison (b , 10 , NewThreadUnsafeSet [int ]())
262
+ }
263
+
264
+ func BenchmarkContainsComparison10Safe (b * testing.B ) {
265
+ benchContainsComparison (b , 10 , NewSet [int ]())
266
+ }
267
+
268
+ func BenchmarkContainsComparison100Unsafe (b * testing.B ) {
269
+ benchContainsComparison (b , 100 , NewThreadUnsafeSet [int ]())
270
+ }
271
+
272
+ func BenchmarkContainsComparison100Safe (b * testing.B ) {
273
+ benchContainsComparison (b , 100 , NewSet [int ]())
274
+ }
275
+
183
276
func benchEqual (b * testing.B , n int , s , t Set [int ]) {
184
277
nums := nrand (n )
185
278
for _ , v := range nums {
0 commit comments