1 /*
2  * Copyright (C) 2021 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package benchmarks.regression;
18 
19 import com.google.caliper.BeforeExperiment;
20 import com.google.caliper.Benchmark;
21 import com.google.caliper.Param;
22 
23 import java.io.ByteArrayInputStream;
24 import java.util.Random;
25 import java.util.Scanner;
26 
27 public class ScannerBenchmark {
28 
29     private static final Random RANDOM = new Random();
30 
31     enum LineLength {
32         TINY(1, 5),
33         SHORT(10, 50),
34         MEDIUM(100, 1_000),
35         LONG(10_000, 50_000);
36 
37         private final int from;
38         private final int to;
39 
LineLength(int from, int to)40         LineLength(int from, int to) {
41             this.from = from;
42             this.to = to;
43         }
44 
get()45         int get() {
46             return RANDOM.nextInt(to - from) + from;
47         }
48 
getMax()49         int getMax() {
50             return to;
51         }
52     }
53 
54     @Param({"TINY", "SHORT", "MEDIUM"})
55     private LineLength lineLength;
56 
57     @Param({"1", "5", "10", "100", "1000", "10000", "25000"})
58     private int linesCount;
59 
60     private byte[] data;
61     private int size;
62 
63     @BeforeExperiment
setUp()64     void setUp() {
65         data = new byte[lineLength.getMax() * linesCount];
66         size = 0;
67 
68         for (int i = 0; i < linesCount; ++i) {
69             append(makeString(lineLength.get()));
70             append("\n");
71         }
72 
73         byte[] temp = new byte[size];
74         System.arraycopy(data, 0, temp, 0, size);
75         data = temp;
76     }
77 
doubleSize()78     private void doubleSize() {
79         byte[] temp = new byte[data.length * 2];
80         System.arraycopy(data, 0, temp, 0, size);
81         data = temp;
82     }
83 
append(String line)84     private void append(String line) {
85         byte[] lineBytes = line.getBytes();
86 
87         while (lineBytes.length + size > data.length) {
88             doubleSize();
89         }
90 
91         System.arraycopy(lineBytes, 0, data, size, lineBytes.length);
92         size += lineBytes.length;
93     }
94 
makeString(int length)95     private String makeString(int length) {
96         StringBuilder builder = new StringBuilder(length);
97 
98         for (int i = 0; i < length; ++i) {
99             builder.append(i % 10).append(", ");
100         }
101 
102         return builder.toString();
103     }
104 
105     @Benchmark
readAll()106     void readAll() {
107         Scanner scanner = new Scanner(new ByteArrayInputStream(data));
108         while (scanner.hasNext()) {
109             scanner.nextLine();
110         }
111     }
112 }
113