1 /* This file is part of the hkl library.
3 * The hkl library is free software: you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation, either version 3 of the License, or
6 * (at your option) any later version.
8 * The hkl library is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
13 * You should have received a copy of the GNU General Public License
14 * along with the hkl library. If not, see <http://www.gnu.org/licenses/>.
16 * Copyright (C) 2003-2010 Synchrotron SOLEIL
17 * L'Orme des Merisiers Saint-Aubin
18 * BP 48 91192 GIF-sur-YVETTE CEDEX
20 * Authors: Picca Frédéric-Emmanuel <picca@synchrotron-soleil.fr>
24 #include <gsl/gsl_sf_trig.h>
26 #include "hkl/hkl-interval.h"
28 /** compare two intervals */
29 int hkl_interval_cmp(HklInterval
const *self
, HklInterval
const *interval
)
31 return self
->min
== interval
->min
&& self
->max
== interval
->max
;
34 /** add two intervals */
35 void hkl_interval_plus_interval(HklInterval
*self
, HklInterval
const *interval
)
37 self
->min
+= interval
->min
;
38 self
->max
+= interval
->max
;
41 /** add to an interval a double */
42 void hkl_interval_plus_double(HklInterval
*self
, double const d
)
49 void hkl_interval_minus_interval(HklInterval
*self
, HklInterval
const *interval
)
51 self
->min
-= interval
->max
;
52 self
->max
-= interval
->min
;
56 void hkl_interval_minus_double(HklInterval
*self
, double const d
)
62 void hkl_interval_times_interval(HklInterval
*self
, HklInterval
const *interval
)
66 double m1
= self
->min
* interval
->min
;
67 double m2
= self
->min
* interval
->max
;
68 double m3
= self
->max
* interval
->min
;
69 double m4
= self
->max
* interval
->max
;
91 void hkl_interval_times_double(HklInterval
*self
, double const d
)
106 void hkl_interval_divides_double(HklInterval
*self
, double const d
)
108 double min
= self
->min
/ d
;
109 double max
= self
->max
/ d
;
119 int hkl_interval_contain_zero(HklInterval
const *self
)
121 if (self
->min
<= 0 && self
->max
>= 0)
127 void hkl_interval_cos(HklInterval
*self
)
134 cmin
= cos(self
->min
);
135 cmax
= cos(self
->max
);
137 if (self
->max
- self
->min
>= 2 * M_PI
) {
144 quad_min
= (int)floor(self
->min
/ M_PI_2
) % 4;
148 quad_max
= (int)floor(self
->max
/ M_PI_2
) % 4;
269 void hkl_interval_acos(HklInterval
*self
)
274 self
->min
= acos(self
->max
);
275 self
->max
= acos(tmp
);
279 void hkl_interval_sin(HklInterval
*self
)
286 smin
= sin(self
->min
);
287 smax
= sin(self
->max
);
289 /* if there is at least one period in b, then a = [-1, 1] */
290 if ( self
->max
- self
->min
>= 2 * M_PI
) {
297 quad_min
= (int)floor(self
->min
/ M_PI_2
) % 4;
301 quad_max
= (int)floor(self
->max
/ M_PI_2
) % 4;
429 void hkl_interval_asin(HklInterval
*self
)
431 self
->min
= asin(self
->min
);
432 self
->max
= asin(self
->max
);
435 void hkl_interval_tan(HklInterval
*self
)
437 int quadrant_down
= (int)floor(self
->min
/ M_PI_2
);
438 int quadrant_up
= (int)floor(self
->max
/ M_PI_2
);
440 /* if there is at least one period in b or if b contains a Pi/2 + k*Pi, */
441 /* then a = ]-oo, +oo[ */
442 if ( ((quadrant_up
- quadrant_down
) >= 2)
443 || (!(quadrant_down
% 2) && (quadrant_up
% 2)) ) {
444 self
->min
= -INFINITY
;
445 self
->max
= INFINITY
;
447 self
->min
= tan(self
->min
);
448 self
->max
= tan(self
->max
);
452 void hkl_interval_atan(HklInterval
*self
)
454 self
->min
= atan(self
->min
);
455 self
->max
= atan(self
->max
);
458 double hkl_interval_length(HklInterval
const *self
)
460 return self
->max
- self
->min
;
463 void hkl_interval_angle_restrict_symm(HklInterval
*self
)
465 gsl_sf_angle_restrict_symm_e(&self
->min
);
466 gsl_sf_angle_restrict_symm_e(&self
->max
);