Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- // gcc.godbolt.org
- // x86-64 CL 19 2017 RTW
- // x86-86 clang 4.0.0, -O2 -Wall -std=c++1z
- // x86-86 gcc 7.1, -O2 -Wall -std=c++1z
- // x86-64 icc 17
- #include <cstddef>
- #include <cassert>
- #include <array>
- namespace
- {
- template <typename ValueT>
- class vector3
- {
- public:
- typedef ValueT value_type;
- typedef ValueT& reference;
- typedef const ValueT& const_reference;
- vector3()
- {
- m_data.fill(ValueT());
- }
- vector3(const_reference x_, const_reference y_, const_reference z_):m_data{x_,y_,z_}
- {
- }
- const_reference x() const
- {
- return m_data[0];
- }
- reference x()
- {
- return m_data[0];
- }
- const_reference y() const
- {
- return m_data[1];
- }
- reference y()
- {
- return m_data[1];
- }
- const_reference z() const
- {
- return m_data[2];
- }
- reference z()
- {
- return m_data[2];
- }
- vector3& operator+=(const vector3& other)
- {
- m_data[0] += other.m_data[0];
- m_data[1] += other.m_data[1];
- m_data[2] += other.m_data[2];
- return *this;
- }
- vector3& operator*=(const_reference value)
- {
- m_data[0] *= value;
- m_data[1] *= value;
- m_data[2] *= value;
- return *this;
- }
- private:
- std::array<value_type, 3> m_data;
- };
- typedef double real_type;
- typedef vector3<real_type> point3;
- template <typename ValueT>
- inline vector3<ValueT> operator*(typename vector3<ValueT>::const_reference a, vector3<ValueT> b)
- {
- return b *= a;
- }
- template <typename ValueT>
- inline vector3<ValueT> operator+(vector3<ValueT> a, const vector3<ValueT>& b)
- {
- return a += b;
- }
- static inline point3 calc(const point3& p_point, const point3& p_direction_x,
- const point3& p_direction_y, const point3& p_direction_z, const point3& p_origin)
- {
- return (p_point.x() * p_direction_x + p_point.y() * p_direction_y + p_point.z() * p_direction_z) + p_origin;
- }
- // 0=run calc function using structs
- // 1=hand inlined calc function using structs
- // 2=hand inlined calc function using x,y,z,direction,origin direct
- // 3=hand optimized result of the calc function
- #define TEST_LEVEL 0
- static point3 test(const real_type& p_x, const real_type& p_y, const real_type& p_z)
- {
- #if TEST_LEVEL == 0 || TEST_LEVEL == 1
- const point3 point(p_x, p_y, p_z);
- const point3 direction_x(0.0, -1.0, 0.0);
- const point3 direction_y(1.0, 0.0, 0.0);
- const point3 direction_z(0.0, 0.0, 1.0);
- const point3 origin(0.0, 0.0, 0.0);
- #endif
- #if TEST_LEVEL == 0
- const point3 result = calc(point, direction_x, direction_y, direction_z, origin);
- #elif TEST_LEVEL == 1
- const point3 result = (point.x() * direction_x + point.y() * direction_y + point.z() * direction_z) + origin;
- #elif TEST_LEVEL == 2
- const point3 result = (p_x * point3(0.0, -1.0, 0.0) + p_y * point3(1.0, 0.0, 0.0) + p_z * point3(0.0, 0.0, 1.0)) + point3(0.0, 0.0, 0.0);
- #elif TEST_LEVEL == 3
- const point3 result(p_y, -p_x, p_z);
- #else
- #error unknown TEST_LEVEL
- #endif
- return result;
- }
- }
- //#define ONLY_CONST_VALUES
- int main(int argc, char* argv[])
- {
- const real_type x = 1.3;
- const real_type y = 2.2;
- const real_type z = 3.1;
- #if defined(ONLY_CONST_VALUES)
- const point3 result = test(x, y, z);
- #else
- //+ argv == anti-optimizer trick
- const point3 result = test(x+argv[0][0], y+argv[0][1], z+argv[0][2]);
- #endif
- const int dummy = (result.x() + result.y() + result.z()) * 1000;
- #if defined(ONLY_CONST_VALUES)
- assert(dummy == 4000);
- #endif
- return dummy; // anti-optimizer-trick
- }
Advertisement
Add Comment
Please, Sign In to add comment