| 168 | } |
| 169 | |
| 170 | template<class T, class Policies> inline |
| 171 | interval<T, Policies> operator*(const interval<T, Policies>& x, |
| 172 | const interval<T, Policies>& y) |
| 173 | { |
| 174 | GECODE_BOOST_USING_STD_MIN(); |
| 175 | GECODE_BOOST_USING_STD_MAX(); |
| 176 | typedef interval<T, Policies> I; |
| 177 | if (interval_lib::detail::test_input(x, y)) |
| 178 | return I::empty(); |
| 179 | typename Policies::rounding rnd; |
| 180 | const T& xl = x.lower(); |
| 181 | const T& xu = x.upper(); |
| 182 | const T& yl = y.lower(); |
| 183 | const T& yu = y.upper(); |
| 184 | |
| 185 | if (interval_lib::user::is_neg(xl)) |
| 186 | if (interval_lib::user::is_pos(xu)) |
| 187 | if (interval_lib::user::is_neg(yl)) |
| 188 | if (interval_lib::user::is_pos(yu)) // M * M |
| 189 | return I(min GECODE_BOOST_PREVENT_MACRO_SUBSTITUTION(rnd.mul_down(xl, yu), rnd.mul_down(xu, yl)), |
| 190 | max GECODE_BOOST_PREVENT_MACRO_SUBSTITUTION(rnd.mul_up (xl, yl), rnd.mul_up (xu, yu)), true); |
| 191 | else // M * N |
| 192 | return I(rnd.mul_down(xu, yl), rnd.mul_up(xl, yl), true); |
| 193 | else |
| 194 | if (interval_lib::user::is_pos(yu)) // M * P |
| 195 | return I(rnd.mul_down(xl, yu), rnd.mul_up(xu, yu), true); |
| 196 | else // M * Z |
| 197 | return I(static_cast<T>(0), static_cast<T>(0), true); |
| 198 | else |
| 199 | if (interval_lib::user::is_neg(yl)) |
| 200 | if (interval_lib::user::is_pos(yu)) // N * M |
| 201 | return I(rnd.mul_down(xl, yu), rnd.mul_up(xl, yl), true); |
| 202 | else // N * N |
| 203 | return I(rnd.mul_down(xu, yu), rnd.mul_up(xl, yl), true); |
| 204 | else |
| 205 | if (interval_lib::user::is_pos(yu)) // N * P |
| 206 | return I(rnd.mul_down(xl, yu), rnd.mul_up(xu, yl), true); |
| 207 | else // N * Z |
| 208 | return I(static_cast<T>(0), static_cast<T>(0), true); |
| 209 | else |
| 210 | if (interval_lib::user::is_pos(xu)) |
| 211 | if (interval_lib::user::is_neg(yl)) |
| 212 | if (interval_lib::user::is_pos(yu)) // P * M |
| 213 | return I(rnd.mul_down(xu, yl), rnd.mul_up(xu, yu), true); |
| 214 | else // P * N |
| 215 | return I(rnd.mul_down(xu, yl), rnd.mul_up(xl, yu), true); |
| 216 | else |
| 217 | if (interval_lib::user::is_pos(yu)) // P * P |
| 218 | return I(rnd.mul_down(xl, yl), rnd.mul_up(xu, yu), true); |
| 219 | else // P * Z |
| 220 | return I(static_cast<T>(0), static_cast<T>(0), true); |
| 221 | else // Z * ? |
| 222 | return I(static_cast<T>(0), static_cast<T>(0), true); |
| 223 | } |
| 224 | |
| 225 | template<class T, class Policies> inline |
| 226 | interval<T, Policies> operator*(const T& x, const interval<T, Policies>& y) |
nothing calls this directly
no test coverage detected