root/OpenSceneGraph/trunk/examples/osgunittests/performance.cpp @ 5226

Revision 5226, 5.1 kB (checked in by robert, 8 years ago)

fixed warning and add a few extra tests

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1#include "performance.h"
2
3#include <osg/Timer>
4#include <iostream>
5
6#include <osg/NodeVisitor>
7#include <osg/ref_ptr>
8#include <osg/MatrixTransform>
9#include <osg/Group>
10
11struct Benchmark
12{
13
14    Benchmark()
15    {
16        calibrate();
17   
18        _beginTick = _timer.tick();
19        _endTick = _timer.tick();
20    }
21   
22    void calibrate(unsigned int numLoops = 100000)
23    {
24        osg::Timer_t beginTick = _timer.tick();
25        for(unsigned int i=0;i<numLoops;++i)
26        {
27            begin();
28            end();
29        }
30        osg::Timer_t endTick = _timer.tick();
31        _averageDelay = _timer.delta_s(beginTick,endTick)/(double)numLoops;
32    }
33   
34    inline void begin()
35    {
36        _beginTick = _timer.tick();
37    }
38
39    inline void end()
40    {
41        _endTick = _timer.tick();
42    }
43
44    inline double time()
45    {
46        double t = _timer.delta_s(_beginTick,_endTick) - _averageDelay;
47        return t<0.0 ? 0.0 : t;
48    }
49
50    inline void output(const char* str, double numIterations=1.0)
51    {
52        std::cout<<str<<"\t";
53        double s = time()/numIterations;
54        if (s>=1.0) std::cout<<s<<" s"<<std::endl;
55        else if (s>=0.001) std::cout<<s*1000.0<<" ms (10 ^ -3)"<<std::endl;
56        else if (s>=0.000001) std::cout<<s*1000000.0<<" ns (10 ^ -6)"<<std::endl;
57        else std::cout<<s*1000000000.0<<" ps (10 ^ -9)"<<std::endl;
58    }
59
60    osg::Timer   _timer;
61    osg::Timer_t _beginTick;
62    osg::Timer_t _endTick;
63    double _averageDelay;
64};
65
66#define RUN(A,B,D) { A.begin(); for(unsigned int i=0;i<D;++i) B; A.end(); A.output(#B,D); }
67
68
69static int v = 0;
70#define OPERATION { v=v+1; }
71
72inline void inline_increment() { OPERATION }
73void function_increment() { OPERATION }
74
75typedef void ( * IncrementProc) ();
76IncrementProc s_functionIncrement = &function_increment;
77inline void functionPointer_increment() { s_functionIncrement(); }
78
79
80struct InlineMethod;
81struct Method;
82struct VirtualMethod;
83struct VirtualMethod2;
84
85struct Visitor
86{
87    virtual void apply(InlineMethod& m);
88    virtual void apply(Method& m);
89    virtual void apply(VirtualMethod& m);
90    virtual void apply(VirtualMethod2& m);
91    virtual ~Visitor() {}
92};
93
94
95struct InlineMethod
96{
97    void method() { OPERATION }
98    virtual void accept(Visitor& visitor) { visitor.apply(*this); }
99    virtual ~InlineMethod() {}
100};
101
102struct Method
103{
104    virtual void accept(Visitor& visitor) { visitor.apply(*this); }
105    void method();
106    virtual ~Method() {}
107};
108
109void Method::method() { OPERATION }
110 
111struct VirtualMethod
112{
113    virtual void accept(Visitor& visitor) { visitor.apply(*this); }
114    virtual void method();
115    virtual ~VirtualMethod() {}
116};
117
118void VirtualMethod::method() { OPERATION }
119
120struct VirtualMethod2 : public VirtualMethod
121{
122    VirtualMethod2() { }
123
124    virtual void accept(Visitor& visitor) { visitor.apply(*this); }
125    virtual void method();
126    virtual ~VirtualMethod2() { }
127   
128    char a[100];
129};
130
131void VirtualMethod2::method() { OPERATION }
132
133void Visitor::apply(Method& m) { m.method(); }
134void Visitor::apply(VirtualMethod& m) { m.method(); }
135void Visitor::apply(InlineMethod& m) { m.method(); }
136void Visitor::apply(VirtualMethod2& m) { m.method(); }
137
138struct CustomVisitor
139{
140    virtual void apply(InlineMethod& m) { m.method(); }
141    virtual void apply(Method& m) { m.method(); }
142    virtual void apply(VirtualMethod& m) { m.method(); }
143    virtual void apply(VirtualMethod2& m) { m.method(); }
144    virtual ~CustomVisitor() {}
145};
146
147class CustomNodeVisitor : public osg::NodeVisitor
148{
149public:
150    void apply(osg::Node&) { }
151    void apply(osg::Group&) { }
152    void apply(osg::Transform&) { }
153};
154
155
156void runPerformanceTests()
157{
158    Benchmark benchmark;
159   
160    unsigned int iterations = 10000000;
161
162    RUN(benchmark, {} , iterations)
163
164    v = 0;
165    RUN(benchmark, OPERATION , iterations)
166    RUN(benchmark, functionPointer_increment() , iterations)
167    RUN(benchmark, inline_increment() , iterations)
168    RUN(benchmark, function_increment() , iterations)
169
170    VirtualMethod2 m4;
171    RUN(benchmark, m4.method() , iterations)
172
173    InlineMethod m1;
174    RUN(benchmark, m1.method() , iterations)
175
176    Method m2;
177    RUN(benchmark, m2.method() , iterations)
178
179    VirtualMethod m3;
180    RUN(benchmark, m3.method() , iterations)
181    RUN(benchmark, m3.method() , iterations)
182
183    Visitor visitor;
184    RUN(benchmark, m4.accept(visitor), iterations)
185    RUN(benchmark, m1.accept(visitor), iterations)
186    RUN(benchmark, m2.accept(visitor), iterations)
187    RUN(benchmark, m3.accept(visitor), iterations)
188    RUN(benchmark, m4.accept(visitor), iterations)
189
190    VirtualMethod* vm4 = &m4;
191
192    RUN(benchmark, (dynamic_cast<VirtualMethod2*>(vm4))->method(), iterations)
193    RUN(benchmark, (static_cast<VirtualMethod2*>(vm4))->method(), iterations)
194    RUN(benchmark, { VirtualMethod mm; mm.method(); }, iterations)
195    RUN(benchmark, { VirtualMethod2 mm; mm.method(); }, iterations)
196
197
198    osg::ref_ptr<osg::Group> group = new osg::Group;
199    osg::ref_ptr<osg::MatrixTransform> mt = new osg::MatrixTransform;
200    osg::Node* m = mt.get();
201    CustomNodeVisitor cnv;
202    RUN(benchmark, { osg::MatrixTransform* mtl = dynamic_cast<osg::MatrixTransform*>(m); if (mtl) cnv.apply(*mtl); }, 1000)
203    RUN(benchmark, { m->accept(cnv); }, 10000)
204   
205}
Note: See TracBrowser for help on using the browser.