pow_zi.c 851 B

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960
  1. #include "f2c.h"
  2. #ifdef __cplusplus
  3. extern "C" {
  4. #endif
  5. #ifdef KR_headers
  6. VOID pow_zi(p, a, b) /* p = a**b */
  7. doublecomplex *p, *a; integer *b;
  8. #else
  9. extern void z_div(doublecomplex*, doublecomplex*, doublecomplex*);
  10. void pow_zi(doublecomplex *p, doublecomplex *a, integer *b) /* p = a**b */
  11. #endif
  12. {
  13. integer n;
  14. unsigned long u;
  15. double t;
  16. doublecomplex q, x;
  17. static doublecomplex one = {1.0, 0.0};
  18. n = *b;
  19. q.r = 1;
  20. q.i = 0;
  21. if(n == 0)
  22. goto done;
  23. if(n < 0)
  24. {
  25. n = -n;
  26. z_div(&x, &one, a);
  27. }
  28. else
  29. {
  30. x.r = a->r;
  31. x.i = a->i;
  32. }
  33. for(u = n; ; )
  34. {
  35. if(u & 01)
  36. {
  37. t = q.r * x.r - q.i * x.i;
  38. q.i = q.r * x.i + q.i * x.r;
  39. q.r = t;
  40. }
  41. if(u >>= 1)
  42. {
  43. t = x.r * x.r - x.i * x.i;
  44. x.i = 2 * x.r * x.i;
  45. x.r = t;
  46. }
  47. else
  48. break;
  49. }
  50. done:
  51. p->i = q.i;
  52. p->r = q.r;
  53. }
  54. #ifdef __cplusplus
  55. }
  56. #endif