rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 1 | /* |
| 2 | * Copyright 2012 Google Inc. |
| 3 | * |
| 4 | * Use of this source code is governed by a BSD-style license that can be |
| 5 | * found in the LICENSE file. |
| 6 | */ |
| 7 | |
Mike Klein | c0bd9f9 | 2019-04-23 12:05:21 -0500 | [diff] [blame] | 8 | #include "bench/Benchmark.h" |
| 9 | #include "include/core/SkCanvas.h" |
| 10 | #include "include/core/SkString.h" |
John Stiles | 9d5461f | 2020-07-27 15:53:49 -0400 | [diff] [blame] | 11 | #include "include/private/SkTemplates.h" |
Mike Klein | c0bd9f9 | 2019-04-23 12:05:21 -0500 | [diff] [blame] | 12 | #include "include/utils/SkRandom.h" |
| 13 | #include "src/core/SkRTree.h" |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 14 | |
| 15 | // confine rectangles to a smallish area, so queries generally hit something, and overlap occurs: |
mtklein | 533eb78 | 2014-08-27 10:39:42 -0700 | [diff] [blame] | 16 | static const SkScalar GENERATE_EXTENTS = 1000.0f; |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 17 | static const int NUM_BUILD_RECTS = 500; |
| 18 | static const int NUM_QUERY_RECTS = 5000; |
sglez@google.com | 8c90212 | 2013-08-30 17:27:47 +0000 | [diff] [blame] | 19 | static const int GRID_WIDTH = 100; |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 20 | |
mtklein | 533eb78 | 2014-08-27 10:39:42 -0700 | [diff] [blame] | 21 | typedef SkRect (*MakeRectProc)(SkRandom&, int, int); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 22 | |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 23 | // Time how long it takes to build an R-Tree. |
tfarina | f168b86 | 2014-06-19 12:32:29 -0700 | [diff] [blame] | 24 | class RTreeBuildBench : public Benchmark { |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 25 | public: |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 26 | RTreeBuildBench(const char* name, MakeRectProc proc) : fProc(proc) { |
mtklein | 4477c3c | 2014-10-27 10:27:10 -0700 | [diff] [blame] | 27 | fName.printf("rtree_%s_build", name); |
rileya@google.com | 61348d1 | 2012-09-06 13:38:53 +0000 | [diff] [blame] | 28 | } |
commit-bot@chromium.org | 644629c | 2013-11-21 06:21:58 +0000 | [diff] [blame] | 29 | |
mtklein | 36352bf | 2015-03-25 18:17:31 -0700 | [diff] [blame] | 30 | bool isSuitableFor(Backend backend) override { |
commit-bot@chromium.org | 644629c | 2013-11-21 06:21:58 +0000 | [diff] [blame] | 31 | return backend == kNonRendering_Backend; |
| 32 | } |
| 33 | |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 34 | protected: |
mtklein | 36352bf | 2015-03-25 18:17:31 -0700 | [diff] [blame] | 35 | const char* onGetName() override { |
rileya@google.com | 61348d1 | 2012-09-06 13:38:53 +0000 | [diff] [blame] | 36 | return fName.c_str(); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 37 | } |
mtklein | a1ebeb2 | 2015-10-01 09:43:39 -0700 | [diff] [blame] | 38 | void onDraw(int loops, SkCanvas* canvas) override { |
commit-bot@chromium.org | e0e7cfe | 2013-09-09 20:09:12 +0000 | [diff] [blame] | 39 | SkRandom rand; |
mtklein | 4477c3c | 2014-10-27 10:27:10 -0700 | [diff] [blame] | 40 | SkAutoTMalloc<SkRect> rects(NUM_BUILD_RECTS); |
| 41 | for (int i = 0; i < NUM_BUILD_RECTS; ++i) { |
| 42 | rects[i] = fProc(rand, i, NUM_BUILD_RECTS); |
| 43 | } |
| 44 | |
commit-bot@chromium.org | 3361471 | 2013-12-03 18:17:16 +0000 | [diff] [blame] | 45 | for (int i = 0; i < loops; ++i) { |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 46 | SkRTree tree; |
mtklein | bfd5bff | 2015-02-10 13:44:27 -0800 | [diff] [blame] | 47 | tree.insert(rects.get(), NUM_BUILD_RECTS); |
halcanary | 96fcdcc | 2015-08-27 07:41:13 -0700 | [diff] [blame] | 48 | SkASSERT(rects != nullptr); // It'd break this bench if the tree took ownership of rects. |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 49 | } |
| 50 | } |
| 51 | private: |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 52 | MakeRectProc fProc; |
rileya@google.com | 61348d1 | 2012-09-06 13:38:53 +0000 | [diff] [blame] | 53 | SkString fName; |
John Stiles | 7571f9e | 2020-09-02 22:42:33 -0400 | [diff] [blame] | 54 | using INHERITED = Benchmark; |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 55 | }; |
| 56 | |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 57 | // Time how long it takes to perform queries on an R-Tree. |
tfarina | f168b86 | 2014-06-19 12:32:29 -0700 | [diff] [blame] | 58 | class RTreeQueryBench : public Benchmark { |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 59 | public: |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 60 | RTreeQueryBench(const char* name, MakeRectProc proc) : fProc(proc) { |
mtklein | 4477c3c | 2014-10-27 10:27:10 -0700 | [diff] [blame] | 61 | fName.printf("rtree_%s_query", name); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 62 | } |
commit-bot@chromium.org | 644629c | 2013-11-21 06:21:58 +0000 | [diff] [blame] | 63 | |
mtklein | 36352bf | 2015-03-25 18:17:31 -0700 | [diff] [blame] | 64 | bool isSuitableFor(Backend backend) override { |
commit-bot@chromium.org | 644629c | 2013-11-21 06:21:58 +0000 | [diff] [blame] | 65 | return backend == kNonRendering_Backend; |
| 66 | } |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 67 | protected: |
mtklein | 36352bf | 2015-03-25 18:17:31 -0700 | [diff] [blame] | 68 | const char* onGetName() override { |
rileya@google.com | 61348d1 | 2012-09-06 13:38:53 +0000 | [diff] [blame] | 69 | return fName.c_str(); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 70 | } |
joshualitt | 8a6697a | 2015-09-30 12:11:07 -0700 | [diff] [blame] | 71 | void onDelayedSetup() override { |
commit-bot@chromium.org | e0e7cfe | 2013-09-09 20:09:12 +0000 | [diff] [blame] | 72 | SkRandom rand; |
mtklein | 4477c3c | 2014-10-27 10:27:10 -0700 | [diff] [blame] | 73 | SkAutoTMalloc<SkRect> rects(NUM_QUERY_RECTS); |
| 74 | for (int i = 0; i < NUM_QUERY_RECTS; ++i) { |
| 75 | rects[i] = fProc(rand, i, NUM_QUERY_RECTS); |
commit-bot@chromium.org | 7fb83c8 | 2013-08-01 15:58:07 +0000 | [diff] [blame] | 76 | } |
mtklein | bfd5bff | 2015-02-10 13:44:27 -0800 | [diff] [blame] | 77 | fTree.insert(rects.get(), NUM_QUERY_RECTS); |
commit-bot@chromium.org | 7fb83c8 | 2013-08-01 15:58:07 +0000 | [diff] [blame] | 78 | } |
| 79 | |
mtklein | a1ebeb2 | 2015-10-01 09:43:39 -0700 | [diff] [blame] | 80 | void onDraw(int loops, SkCanvas* canvas) override { |
commit-bot@chromium.org | e0e7cfe | 2013-09-09 20:09:12 +0000 | [diff] [blame] | 81 | SkRandom rand; |
commit-bot@chromium.org | 3361471 | 2013-12-03 18:17:16 +0000 | [diff] [blame] | 82 | for (int i = 0; i < loops; ++i) { |
Mike Klein | 508fd32 | 2020-02-12 09:45:41 -0600 | [diff] [blame] | 83 | std::vector<int> hits; |
mtklein | 533eb78 | 2014-08-27 10:39:42 -0700 | [diff] [blame] | 84 | SkRect query; |
mtklein | 4477c3c | 2014-10-27 10:27:10 -0700 | [diff] [blame] | 85 | query.fLeft = rand.nextRangeF(0, GENERATE_EXTENTS); |
| 86 | query.fTop = rand.nextRangeF(0, GENERATE_EXTENTS); |
| 87 | query.fRight = query.fLeft + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/2); |
| 88 | query.fBottom = query.fTop + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/2); |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 89 | fTree.search(query, &hits); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 90 | } |
| 91 | } |
| 92 | private: |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 93 | SkRTree fTree; |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 94 | MakeRectProc fProc; |
rileya@google.com | 61348d1 | 2012-09-06 13:38:53 +0000 | [diff] [blame] | 95 | SkString fName; |
John Stiles | 7571f9e | 2020-09-02 22:42:33 -0400 | [diff] [blame] | 96 | using INHERITED = Benchmark; |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 97 | }; |
| 98 | |
mtklein | 533eb78 | 2014-08-27 10:39:42 -0700 | [diff] [blame] | 99 | static inline SkRect make_XYordered_rects(SkRandom& rand, int index, int numRects) { |
| 100 | SkRect out; |
| 101 | out.fLeft = SkIntToScalar(index % GRID_WIDTH); |
| 102 | out.fTop = SkIntToScalar(index / GRID_WIDTH); |
| 103 | out.fRight = out.fLeft + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/3); |
| 104 | out.fBottom = out.fTop + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/3); |
sglez@google.com | 8c90212 | 2013-08-30 17:27:47 +0000 | [diff] [blame] | 105 | return out; |
| 106 | } |
mtklein | 533eb78 | 2014-08-27 10:39:42 -0700 | [diff] [blame] | 107 | static inline SkRect make_YXordered_rects(SkRandom& rand, int index, int numRects) { |
| 108 | SkRect out; |
| 109 | out.fLeft = SkIntToScalar(index / GRID_WIDTH); |
| 110 | out.fTop = SkIntToScalar(index % GRID_WIDTH); |
| 111 | out.fRight = out.fLeft + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/3); |
| 112 | out.fBottom = out.fTop + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/3); |
sglez@google.com | 8c90212 | 2013-08-30 17:27:47 +0000 | [diff] [blame] | 113 | return out; |
| 114 | } |
| 115 | |
mtklein | 533eb78 | 2014-08-27 10:39:42 -0700 | [diff] [blame] | 116 | static inline SkRect make_random_rects(SkRandom& rand, int index, int numRects) { |
| 117 | SkRect out; |
| 118 | out.fLeft = rand.nextRangeF(0, GENERATE_EXTENTS); |
| 119 | out.fTop = rand.nextRangeF(0, GENERATE_EXTENTS); |
| 120 | out.fRight = out.fLeft + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/5); |
| 121 | out.fBottom = out.fTop + 1 + rand.nextRangeF(0, GENERATE_EXTENTS/5); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 122 | return out; |
| 123 | } |
| 124 | |
mtklein | a06a953 | 2014-11-18 09:27:49 -0800 | [diff] [blame] | 125 | static inline SkRect make_concentric_rects(SkRandom&, int index, int numRects) { |
| 126 | return SkRect::MakeWH(SkIntToScalar(index+1), SkIntToScalar(index+1)); |
| 127 | } |
| 128 | |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 129 | /////////////////////////////////////////////////////////////////////////////// |
| 130 | |
halcanary | 385fe4d | 2015-08-26 13:07:48 -0700 | [diff] [blame] | 131 | DEF_BENCH(return new RTreeBuildBench("XY", &make_XYordered_rects)); |
| 132 | DEF_BENCH(return new RTreeBuildBench("YX", &make_YXordered_rects)); |
| 133 | DEF_BENCH(return new RTreeBuildBench("random", &make_random_rects)); |
| 134 | DEF_BENCH(return new RTreeBuildBench("concentric", &make_concentric_rects)); |
rileya@google.com | 981b33a | 2012-09-05 18:36:17 +0000 | [diff] [blame] | 135 | |
halcanary | 385fe4d | 2015-08-26 13:07:48 -0700 | [diff] [blame] | 136 | DEF_BENCH(return new RTreeQueryBench("XY", &make_XYordered_rects)); |
| 137 | DEF_BENCH(return new RTreeQueryBench("YX", &make_YXordered_rects)); |
| 138 | DEF_BENCH(return new RTreeQueryBench("random", &make_random_rects)); |
| 139 | DEF_BENCH(return new RTreeQueryBench("concentric", &make_concentric_rects)); |