|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r49503 - in sandbox/mp_math: boost/mp_math/mp_int boost/mp_math/mp_int/detail libs/mp_math/test
From: baraclese_at_[hidden]
Date: 2008-10-31 19:37:03
Author: baraclese
Date: 2008-10-31 19:37:02 EDT (Fri, 31 Oct 2008)
New Revision: 49503
URL: http://svn.boost.org/trac/boost/changeset/49503
Log:
* added <limits> include to traits.hpp
* <boost/mp_math/mp_int/detail/primitive_ops.hpp>:
- improved performance of comba_mul and comba_sqr slightly
- minor stylistic changes
Text files modified:
sandbox/mp_math/boost/mp_math/mp_int/detail/primitive_ops.hpp | 133 +++++++++++++++++++++------------------
sandbox/mp_math/boost/mp_math/mp_int/traits.hpp | 1
sandbox/mp_math/libs/mp_math/test/mul.cpp | 2
3 files changed, 72 insertions(+), 64 deletions(-)
Modified: sandbox/mp_math/boost/mp_math/mp_int/detail/primitive_ops.hpp
==============================================================================
--- sandbox/mp_math/boost/mp_math/mp_int/detail/primitive_ops.hpp (original)
+++ sandbox/mp_math/boost/mp_math/mp_int/detail/primitive_ops.hpp 2008-10-31 19:37:02 EDT (Fri, 31 Oct 2008)
@@ -86,23 +86,23 @@
digit_type x);
// z = x * y
- static void classic_mul(digit_type* z, const digit_type* x, size_type x_size,
- const digit_type* y, size_type y_size);
+ static void classic_mul(digit_type* z, const digit_type* x, size_type xlen,
+ const digit_type* y, size_type ylen);
- // z = x * y; precondition: x_size >= y_size
- static void comba_mul(digit_type* z, const digit_type* x, size_type x_size,
- const digit_type* y, size_type y_size);
+ // z = x * y; precondition: xlen >= ylen
+ static void comba_mul(digit_type* z, const digit_type* x, size_type xlen,
+ const digit_type* y, size_type ylen);
// z = x * y; for numbers of the same size
static void comba_mul(digit_type* z,
const digit_type* x,
- const digit_type* y, size_type xy_size);
-
+ const digit_type* y, size_type xylen);
+
// SQR ------------------------------------
// z = x * x;
- static void comba_sqr(digit_type* z, const digit_type* x, size_type x_size);
-
+ static void comba_sqr(digit_type* z, const digit_type* x, size_type xlen);
+
// MADD ------------------------------------
// z = w * x + y
@@ -300,14 +300,14 @@
template<typename D, typename W, typename S>
void
basic_primitive_ops<D,W,S>::classic_mul(
- digit_type* z, const digit_type* x, size_type x_size,
- const digit_type* y, size_type y_size)
+ digit_type* z, const digit_type* x, size_type xlen,
+ const digit_type* y, size_type ylen)
{
// phase 1
word_type tmp = static_cast<word_type>(x[0]) * static_cast<word_type>(y[0]);
z[0] = static_cast<digit_type>(tmp);
- for (size_type i = 1; i < x_size; ++i)
+ for (size_type i = 1; i < xlen; ++i)
{
tmp = (tmp >> digit_bits)
+ static_cast<word_type>(x[i])
@@ -316,17 +316,17 @@
}
tmp >>= digit_bits;
- z[x_size] = static_cast<digit_type>(tmp);
+ z[xlen] = static_cast<digit_type>(tmp);
// phase 2
- for (size_type i = 1; i < y_size; ++i)
+ for (size_type i = 1; i < ylen; ++i)
{
tmp = static_cast<word_type>(y[i])
* static_cast<word_type>(x[0])
+ static_cast<word_type>(z[i]);
z[i] = static_cast<digit_type>(tmp);
- for (size_type j = 1; j < x_size; ++j)
+ for (size_type j = 1; j < xlen; ++j)
{
tmp = (tmp >> digit_bits)
+ static_cast<word_type>(y[i]) * static_cast<word_type>(x[j])
@@ -335,7 +335,7 @@
}
tmp >>= digit_bits;
- z[i + x_size] = static_cast<digit_type>(tmp);
+ z[i + xlen] = static_cast<digit_type>(tmp);
}
}
@@ -357,68 +357,69 @@
// operator *= (). Just check if (smaller number).used_ >= overflow_count.
template<typename D, typename W, typename S>
void
-basic_primitive_ops<D,W,S>::comba_mul(
- digit_type* z, const digit_type* x, size_type x_size,
- const digit_type* y, size_type y_size)
+basic_primitive_ops<D,W,S>::comba_mul(digit_type* z,
+ const digit_type* x, size_type xlen,
+ const digit_type* y, size_type ylen)
{
- assert(x_size >= y_size);
-
- const size_type k = x_size + y_size;
+ assert(xlen >= ylen);
- word_type acc = 0; // accumulator in each column
+ word_type acc = 0; // accumulator for each column
word_type carry = 0;
// phase 1
- for (size_type i = 0; i < y_size; ++i)
+ for (size_type i = 0; i < ylen; ++i)
{
+ const digit_type* a = x;
+ const digit_type* b = y + i;
+
for (size_type j = 0; j <= i; ++j)
{
- const word_type r = static_cast<word_type>(y[j])
- * static_cast<word_type>(x[i-j]);
- acc += r;
+ acc += static_cast<word_type>(*a++) * static_cast<word_type>(*b--);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
}
-
+
// phase 2
- for (size_type i = 0; i < x_size - y_size; ++i)
+ for (size_type i = 0; i < xlen - ylen; ++i)
{
- size_type j = 0;
- size_type m = y_size;
- while (j < y_size)
+ const digit_type* a = x + ylen + i;
+ const digit_type* b = y;
+
+ for (size_type j = 0; j < ylen; ++j)
{
- const word_type r = static_cast<word_type>(y[j])
- * static_cast<word_type>(x[m+i]);
- acc += r;
+ acc += static_cast<word_type>(*a--) * static_cast<word_type>(*b++);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
- ++j; --m;
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
}
// phase 3
- for (size_type i = x_size; i < k - 1; ++i)
+ for (size_type i = 0; i < ylen - 1; ++i)
{
- for (size_type j = y_size - (k - i - 1); j < y_size; ++j)
+ const digit_type* a = x + xlen - 1;
+ const digit_type* b = y + i + 1;
+
+ for (size_type j = i + 1; j < ylen; ++j)
{
- const word_type r = static_cast<word_type>(y[j])
- * static_cast<word_type>(x[i-j]);
- acc += r;
+ acc += static_cast<word_type>(*a--) * static_cast<word_type>(*b++);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
}
-
+
*z = static_cast<digit_type>(acc);
}
@@ -426,38 +427,42 @@
void
basic_primitive_ops<D,W,S>::comba_mul(digit_type* z,
const digit_type* x,
- const digit_type* y, size_type xy_size)
+ const digit_type* y, size_type xylen)
{
word_type acc = 0; // accumulator for each column
word_type carry = 0;
// phase 1
- for (size_type i = 0; i < xy_size; ++i)
+ for (size_type i = 0; i < xylen; ++i)
{
+ const digit_type* a = x;
+ const digit_type* b = y + i;
+
for (size_type j = 0; j <= i; ++j)
{
- const word_type r = static_cast<word_type>(x[j])
- * static_cast<word_type>(y[i-j]);
- acc += r;
+ acc += static_cast<word_type>(*a++) * static_cast<word_type>(*b--);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
}
// phase 2
- for (size_type i = xy_size; i < 2 * xy_size - 1; ++i)
+ for (size_type i = 1; i < xylen; ++i)
{
- for (size_type j = i - xy_size + 1; j < xy_size; ++j)
+ const digit_type* a = y + xylen - 1;
+ const digit_type* b = x + i;
+
+ for (size_type j = 0; j < xylen - i; ++j)
{
- const word_type r = static_cast<word_type>(x[j])
- * static_cast<word_type>(y[i-j]);
- acc += r;
+ acc += static_cast<word_type>(*a--) * static_cast<word_type>(*b++);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
@@ -470,38 +475,42 @@
void
basic_primitive_ops<D,W,S>::comba_sqr(digit_type* z,
const digit_type* x,
- size_type x_size)
+ size_type xlen)
{
word_type acc = 0; // accumulator for each column
word_type carry = 0;
// phase 1
- for (size_type i = 0; i < x_size; ++i)
+ for (size_type i = 0; i < xlen; ++i)
{
+ const digit_type* a = x;
+ const digit_type* b = x + i;
+
for (size_type j = 0; j <= i; ++j)
{
- const word_type r = static_cast<word_type>(x[j])
- * static_cast<word_type>(x[i-j]);
- acc += r;
+ acc += static_cast<word_type>(*a++) * static_cast<word_type>(*b--);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
}
// phase 2
- for (size_type i = x_size; i < 2 * x_size - 1; ++i)
+ for (size_type i = 1; i < xlen; ++i)
{
- for (size_type j = i - x_size + 1; j < x_size; ++j)
+ const digit_type* a = x + xlen - 1;
+ const digit_type* b = x + i;
+
+ for (size_type j = 0; j < xlen - i; ++j)
{
- const word_type r = static_cast<word_type>(x[j])
- * static_cast<word_type>(x[i-j]);
- acc += r;
+ acc += static_cast<word_type>(*a--) * static_cast<word_type>(*b++);
carry += acc >> digit_bits;
acc = static_cast<digit_type>(acc);
}
+
*z++ = static_cast<digit_type>(acc);
acc = static_cast<digit_type>(carry);
carry >>= digit_bits;
Modified: sandbox/mp_math/boost/mp_math/mp_int/traits.hpp
==============================================================================
--- sandbox/mp_math/boost/mp_math/mp_int/traits.hpp (original)
+++ sandbox/mp_math/boost/mp_math/mp_int/traits.hpp 2008-10-31 19:37:02 EDT (Fri, 31 Oct 2008)
@@ -7,6 +7,7 @@
#define BOOST_MP_MATH_MP_INT_TRAITS_HPP
#include <cstddef> // size_t
+#include <limits>
#include <boost/config.hpp>
#include <boost/static_assert.hpp>
#include <boost/mpl/back.hpp>
Modified: sandbox/mp_math/libs/mp_math/test/mul.cpp
==============================================================================
--- sandbox/mp_math/libs/mp_math/test/mul.cpp (original)
+++ sandbox/mp_math/libs/mp_math/test/mul.cpp 2008-10-31 19:37:02 EDT (Fri, 31 Oct 2008)
@@ -47,7 +47,6 @@
BOOST_CHECK_EQUAL(z, "43076328327684465744675616648356768900793087398990591539995027544295");
}
-
BOOST_AUTO_TEST_CASE_TEMPLATE(mul6, mp_int_type, mp_int_types)
{
// this tests karatsuba multiplication for 8, 16 and 32 bit digit_type
@@ -365,4 +364,3 @@
BOOST_CHECK_EQUAL(z, w);
}
-
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk