1 // ORIG-DATE:     Dec 2007
2 // -*- Mode : c++ -*-
3 //
4 // SUMMARY  :  Model of $\mathbb{R}^3$
5 // USAGE    : LGPL
6 // ORG      : LJLL Universite Pierre et Marie Curi, Paris,  FRANCE
7 // AUTHOR   : Frederic Hecht
8 // E-MAIL   : frederic.hecht@ann.jussieu.fr
9 //
10 
11 /*
12 
13  This file is part of Freefem++
14 
15  Freefem++ is free software; you can redistribute it and/or modify
16  it under the terms of the GNU Lesser General Public License as published by
17  the Free Software Foundation; either version 2.1 of the License, or
18  (at your option) any later version.
19 
20  Freefem++  is distributed in the hope that it will be useful,
21  but WITHOUT ANY WARRANTY; without even the implied warranty of
22  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23  GNU Lesser General Public License for more details.
24 
25  You should have received a copy of the GNU Lesser General Public License
26  along with Freefem++; if not, write to the Free Software
27  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
28 
29  Thank to the ARN ()  FF2A3 grant
30  ref:ANR-07-CIS7-002-01
31  */
32 
33 #ifndef R3_HPP
34 #define  R3_HPP
35 #include "R1.hpp"
36 #include "R2.hpp"
37 
38 class R3  {
39 
40 public:
41   typedef double R;
42 
43   static const int d=3;
44 
45   R x,y,z;
46 
R3()47   R3 () :x(0),y(0),z(0) {};
R3(R a,R b,R c)48   R3 (R a,R b,R c):x(a),y(b),z(c)  {}
R3(const R * a)49   R3 (const R * a):x(a[0]),y(a[1]) ,z(a[2]) {}
50 
R3(R2 P2)51   R3 (R2 P2):x(P2.x),y(P2.y),z(0)  {}
R3(R1 P2)52   R3 (R1 P2):x(P2.x),y(0),z(0)  {}
R3(R0)53   R3 (R0 ): x(0),y(0),z(0) {}
R3(R2 P2,R zz)54   R3 (R2 P2,R zz):x(P2.x),y(P2.y),z(zz)  {}
R3(const R3 & A,const R3 & B)55   R3 (const R3 & A,const R3 & B) :x(B.x-A.x),y(B.y-A.y),z(B.z-A.z)  {}
diag(R a)56   static  R3 diag(R a){ return R3(a,a,a);}
operator =(const R2 & P2)57   R3 & operator=(const R2 &P2) {x=P2.x;y=P2.y;z=0.;return *this;}
operator =(const R1 & P2)58   R3 & operator=(const R1 &P2) {x=P2.x;y=0.;z=0.;return *this;}
operator +(const R3 & P) const59   R3   operator+(const R3 &P)const   {return R3(x+P.x,y+P.y,z+P.z);}
operator +=(const R3 & P)60   R3 & operator+=(const R3 &P)  {x += P.x;y += P.y;z += P.z;return *this;}
operator -(const R3 & P) const61   R3   operator-(const R3 &P)const   {return R3(x-P.x,y-P.y,z-P.z);}
operator -=(const R3 & P)62   R3 & operator-=(const R3 &P) {x -= P.x;y -= P.y;z -= P.z;return *this;}
operator *=(R c)63   R3 & operator*=(R c) {x *= c;y *= c;z *= c;return *this;}
operator /=(R c)64   R3 & operator/=(R c) {x /= c;y /= c;z /= c;return *this;}
operator -() const65   R3   operator-()const  {return R3(-x,-y,-z);}
operator +() const66   R3   operator+()const  {return *this;}
operator ,(const R3 & P) const67   R    operator,(const R3 &P)const  {return  x*P.x+y*P.y+z*P.z;} // produit scalaire
operator ^(const R3 & P) const68   R3  operator^(const R3 &P)const {return R3(y*P.z-z*P.y ,P.x*z-x*P.z, x*P.y-y*P.x);} // produit vectoreil
operator *(R c) const69   R3   operator*(R c)const {return R3(x*c,y*c,z*c);}
operator /(R c) const70   R3   operator/(R c)const {return R3(x/c,y/c,z/c);}
operator [](int i)71   R  &  operator[](int i){ return (&x)[i];}
operator [](int i) const72   const R  &  operator[](int i) const { return (&x)[i];}
operator *(R c,const R3 & P)73   friend R3 operator*(R c,const R3 &P) {return P*c;}
operator /(R c,const R3 & P)74   friend R3 operator/(R c,const R3 &P) {return P/c;}
norme() const75   R norme() const { return std::sqrt(x*x+y*y+z*z);}
norme2() const76   R norme2() const { return (x*x+y*y+z*z);}
sum() const77   R sum() const { return x+y+z;}
toBary(R * b) const78   R * toBary(R * b) const  { b[0]=1.-x-y-z;b[1]=x;b[2]=y;b[3]=z;return b;}
X() const79   R  X() const {return x;}
Y() const80   R  Y() const {return y;}
Z() const81   R  Z() const {return z;}
82 
Bary(const R3 P[d+1]) const83   R3 Bary(const R3 P[d+1]) const { return (1-x-y-z)*P[0]+x*P[1]+y*P[2]+z*P[3];}  // add FH
Bary(const R3 ** P) const84   R3 Bary(const R3 **P ) const { return (1-x-y-z)*(*P[0])+x*(*P[1])+y*(*P[2])+z*(*P[3]);}  // add FH
operator <<(ostream & f,const R3 & P)85   friend ostream& operator <<(ostream& f, const R3 & P )
86   { f << P.x << ' ' << P.y << ' ' << P.z   ; return f; }
operator >>(istream & f,R3 & P)87   friend istream& operator >>(istream& f,  R3 & P)
88   { f >>  P.x >>  P.y >>  P.z  ; return f; }
89 
det(R3 A,R3 B,R3 C)90   friend R det( R3 A, R3 B,  R3 C)
91   {
92     R  s=1.;
93     if(abs(A.x)<abs(B.x)) Exchange(A,B),s = -s;
94     if(abs(A.x)<abs(C.x)) Exchange(A,C),s = -s;
95     if(abs(A.x)>1e-50)
96       {
97 	s *= A.x;
98 	A.y /= A.x; A.z /= A.x;
99 	B.y  -=  A.y*B.x  ;   B.z  -=  A.z*B.x ;
100 	C.y  -=  A.y*C.x  ;   C.z  -=  A.z*C.x ;
101 	return s* ( B.y*C.z - B.z*C.y) ;
102       }
103     else return 0.   ;
104   }
105 
det(const R3 & A,const R3 & B,const R3 & C,const R3 & D)106   friend R  det(const R3 &A,const R3 &B, const R3 &C, const R3 &D) { return det(R3(A,B),R3(A,C),R3(A,D));}
107   static const R3 KHat[d+1];
108 
p2() const109   R2 p2() const { return R2(x,y);}
110 };
111 
Minc(const R3 & A,const R3 & B)112 inline R3 Minc(const R3 & A,const R3 &B){ return R3(min(A.x,B.x),min(A.y,B.y),min(A.z,B.z));}
Maxc(const R3 & A,const R3 & B)113 inline R3 Maxc(const R3 & A,const R3 &B){ return R3(max(A.x,B.x),max(A.y,B.y),max(A.z,B.z));}
Norme_infty(const R3 & A)114 inline R Norme_infty(const R3 & A){return Max(std::fabs(A.x),std::fabs(A.y),std::fabs(A.z));}
Norme2_2(const R3 & A)115 inline R Norme2_2(const R3 & A){ return (A,A);}
Norme2(const R3 & A)116 inline R Norme2(const R3 & A){ return sqrt((A,A));}
117 
Bary(R3 P[d+1]) const118 inline R3 R2::Bary(R3 P[d+1]) const { return (1-x-y)*P[0]+x*P[1]+y*P[2];}  // add FH
Bary(const R3 * const * const P) const119 inline R3 R2::Bary(const R3 *const *const P ) const { return (1-x-y)*(*P[0])+x*(*P[1])+y*(*P[2]);}  // add FH
Bary(R3 P[d+1]) const120 inline R3 R1::Bary(R3 P[d+1]) const { return (1-x)*P[0]+x*P[1];}  // add FH
Bary(const R3 * const * const P) const121 inline R3 R1::Bary(const R3 *const *const P ) const { return (1-x)*(*P[0])+x*(*P[1]);}  // add FH
Bary(R2 P[d+1]) const122 inline R2 R1::Bary(R2 P[d+1]) const { return (1-x)*P[0]+x*P[1];}  // add FH
Bary(const R2 * const * const P) const123 inline R2 R1::Bary(const R2 *const *const P ) const { return (1-x)*(*P[0])+x*(*P[1]);}  // add FH
124 
125 
126 struct lessRd
127 {
operator ()lessRd128   bool operator()(const R1 &s1, const R1 & s2) const
129   {    return s1.x < s2.x ;  }
operator ()lessRd130   bool operator()(const R2 &s1, const R2 & s2) const
131   {    return s1.x == s2.x ? (s1.y < s2.y)  :s1.x < s2.x;  }
operator ()lessRd132   bool operator()(const R3 &s1, const R3 & s2) const
133   {    return s1.x == s2.x ? (s1.y == s2.y ? (s1.z < s2.z)  :s1.y < s2.y )  :s1.x < s2.x;  }
134 };
135 
136 
137 
138 #endif
139 
140