10 real(kind=kreal),
parameter,
private :: pi=3.14159265358979d0
16 integer :: var,dimn,syze,bite
18 var = var + dimn*syze*bite
24 integer,
intent(in) :: iin
25 integer,
pointer :: carray(:)
28 integer,
pointer :: dumarray(:) => null()
29 if( .not.
associated(carray) )
then
33 oldsize =
size( carray )
34 allocate( dumarray(oldsize) )
36 dumarray(i) = carray(i)
39 allocate( carray(oldsize+1) )
41 carray(i) = dumarray(i)
43 carray(oldsize+1) = iin
45 if(
associated(dumarray) )
deallocate( dumarray )
50 real(kind=kreal),
intent(in) :: tensor(6)
51 real(kind=kreal),
intent(out) :: eigval(3)
53 real(kind=kreal) :: i1,i2,i3,r,theta,q, x(3,3), xx(3,3)
54 real(kind=kreal),
parameter :: small = 1.0d-10
56 x(1,1)=tensor(1); x(2,2)=tensor(2); x(3,3)=tensor(3)
57 x(1,2)=tensor(4); x(2,1)=x(1,2)
58 x(2,3)=tensor(5); x(3,2)=x(2,3)
59 x(3,1)=tensor(6); x(1,3)=x(3,1)
62 i1= x(1,1)+x(2,2)+x(3,3)
63 i2= 0.5d0*( i1*i1 - (xx(1,1)+xx(2,2)+xx(3,3)) )
64 i3= x(1,1)*x(2,2)*x(3,3)+x(2,1)*x(3,2)*x(1,3)+x(3,1)*x(1,2)*x(2,3) &
65 -x(3,1)*x(2,2)*x(1,3)-x(2,1)*x(1,2)*x(3,3)-x(1,1)*x(3,2)*x(2,3)
67 r=(-2.d0*i1*i1*i1+9.d0*i1*i2-27.d0*i3)/54.d0
68 q=(i1*i1-3.d0*i2)/9.d0
72 if(r*r - q*q*q > small)
then
73 write(*,*)
'ERROR in tensor_eigen3: Discriminant R^2 - Q^3 > 0'
74 write(*,*)
'This indicates the algorithm has numerical issues.'
75 write(*,*)
'Discriminant =', r*r - q*q*q
76 stop
'Eigenvalue calculation failed - possible numerical error'
80 if(abs(q) < small)
then
87 if(abs(q*q*q) < small)
then
89 if(abs(r) < small)
then
105 theta = acos(max(-1.0d0, min(1.0d0, r/dsqrt(q*q*q))))
108 eigval(1) = -2.d0*dsqrt(q)*cos(theta/3.d0)+i1/3.d0
109 eigval(2) = -2.d0*dsqrt(q)*cos((theta+2.d0*pi)/3.d0)+i1/3.d0
110 eigval(3) = -2.d0*dsqrt(q)*cos((theta-2.d0*pi)/3.d0)+i1/3.d0
117 subroutine eigen3 (tensor, eigval, princ)
118 real(kind=kreal),
intent(in) :: tensor(6)
119 real(kind=kreal),
intent(out) :: eigval(3)
120 real(kind=kreal),
intent(out) :: princ(3, 3)
122 integer,
parameter :: msweep = 50
123 integer :: i,j, is, ip, iq, ir
124 real(kind=kreal) :: fsum, od, theta, t, c, s, tau, g, h, hd, btens(3,3), factor
126 btens(1,1)=tensor(1); btens(2,2)=tensor(2); btens(3,3)=tensor(3)
127 btens(1,2)=tensor(4); btens(2,1)=btens(1,2)
128 btens(2,3)=tensor(5); btens(3,2)=btens(2,3)
129 btens(3,1)=tensor(6); btens(1,3)=btens(3,1)
139 eigval(i) = btens(i, i)
140 factor = factor + dabs(btens(i,i))
143 if( factor == 0.d0 .or. factor /= factor )
then
146 eigval(1:3) = eigval(1:3)/factor
147 btens(1:3,1:3) = btens(1:3,1:3)/factor
157 fsum = fsum + abs( btens(ip, iq) )
163 if ( fsum < 1.d-10 )
then
164 eigval(1:3) = eigval(1:3)*factor
172 od = 100.d0 * abs(btens(ip, iq) )
173 if ( (od+abs(eigval(ip) ) /= abs(eigval(ip) )) &
174 .and. (od+abs(eigval(iq) ) /= abs(eigval(iq) )))
then
175 hd = eigval(iq) - eigval(ip)
179 if ( abs(hd) + od == abs(hd) )
then
180 t = btens(ip, iq) / hd
182 theta = 0.5d0 * hd / btens(ip, iq)
183 t = 1.d0 / (abs(theta) + sqrt(1.d0 + theta**2) )
184 if ( theta < 0.d0 ) t = - t
189 c = 1.d0 / sqrt(1.d0 + t**2)
192 h = t * btens(ip, iq)
193 eigval(ip) = eigval(ip) - h
194 eigval(iq) = eigval(iq) + h
199 g = btens(min(ir, ip), max(ir, ip) )
200 h = btens(min(ir, iq), max(ir, iq) )
201 btens(min(ir, ip), max(ir, ip) ) = g &
203 btens(min(ir, iq), max(ir, iq) ) = h &
211 princ(ir, ip) = g - s * (h + g * tau)
212 princ(ir, iq) = h + s * (g - h * tau)
222 stop
' Jacobi iteration unable to converge'
227 real(kind=kreal) :: mat(6)
228 real(kind=kreal) :: xj(3,3)
230 xj(1,1)=mat(1); xj(2,2)=mat(2); xj(3,3)=mat(3)
231 xj(1,2)=mat(4); xj(2,1)=xj(1,2)
232 xj(2,3)=mat(5); xj(3,2)=xj(2,3)
233 xj(3,1)=mat(6); xj(1,3)=xj(3,1)
236 +xj(2,1)*xj(3,2)*xj(1,3) &
237 +xj(3,1)*xj(1,2)*xj(2,3) &
238 -xj(3,1)*xj(2,2)*xj(1,3) &
239 -xj(2,1)*xj(1,2)*xj(3,3) &
240 -xj(1,1)*xj(3,2)*xj(2,3)
245 real(kind=kreal) :: xj(3,3)
248 +xj(2,1)*xj(3,2)*xj(1,3) &
249 +xj(3,1)*xj(1,2)*xj(2,3) &
250 -xj(3,1)*xj(2,2)*xj(1,3) &
251 -xj(2,1)*xj(1,2)*xj(3,3) &
252 -xj(1,1)*xj(3,2)*xj(2,3)
257 character(*) :: sub_name
258 integer(kind=kint) :: imsg
259 integer(kind=kint) :: ierr
262 write(imsg,*)
'Memory overflow at ', sub_name
263 write(*,*)
'Memory overflow at ', sub_name
264 call hecmw_abort( hecmw_comm_get_comm( ) )
270 integer,
intent(in) :: NN
271 real(kind=kreal),
intent(inout) :: a(nn,nn)
273 integer :: I, J,K,IW,LR,IP(NN)
274 real(kind=kreal) :: w,wmax,pivot,api,eps,det
294 write(*,
'(''PIVOT ERROR AT'',I5)') k
318 if (j.NE.k) a(i,j)=a(i,j)-w*a(k,j)
345 integer,
intent(in) :: NN
346 real(kind=kreal),
intent(inout) :: a(nn,nn)
347 real(kind=kreal),
intent(inout) :: b(nn)
349 integer :: i, j, k, imax
350 real(kind=kreal) :: w, piv
356 if( dabs(a(i,k)) > dabs(a(imax,k)) ) imax = i
360 w = a(k,j); a(k,j) = a(imax,j); a(imax,j) = w
362 w = b(k); b(k) = b(imax); b(imax) = w
368 a(i,j) = a(i,j) - w * a(k,j)
370 b(i) = b(i) - w * b(k)
376 b(i) = b(i) - a(i,j) * b(j)
383 real(kind=kreal),
intent(in) :: v1(3),v2(3)
384 real(kind=kreal),
intent(out) :: vn(3)
386 vn(1) = v1(2)*v2(3) - v1(3)*v2(2)
387 vn(2) = v1(3)*v2(1) - v1(1)*v2(3)
388 vn(3) = v1(1)*v2(2) - v1(2)*v2(1)
392 real(kind=kreal),
intent(in) :: jacob(3,3)
393 real(kind=kreal),
intent(out) :: tm(6,6)
399 tm(i,j)= jacob(i,j)*jacob(i,j)
401 tm(i,4) = jacob(i,1)*jacob(i,2)
402 tm(i,5) = jacob(i,2)*jacob(i,3)
403 tm(i,6) = jacob(i,3)*jacob(i,1)
405 tm(4,1) = 2.d0*jacob(1,1)*jacob(2,1)
406 tm(5,1) = 2.d0*jacob(2,1)*jacob(3,1)
407 tm(6,1) = 2.d0*jacob(3,1)*jacob(1,1)
408 tm(4,2) = 2.d0*jacob(1,2)*jacob(2,2)
409 tm(5,2) = 2.d0*jacob(2,2)*jacob(3,2)
410 tm(6,2) = 2.d0*jacob(3,2)*jacob(1,2)
411 tm(4,3) = 2.d0*jacob(1,3)*jacob(2,3)
412 tm(5,3) = 2.d0*jacob(2,3)*jacob(3,3)
413 tm(6,3) = 2.d0*jacob(3,3)*jacob(1,3)
414 tm(4,4) = jacob(1,1)*jacob(2,2) + jacob(1,2)*jacob(2,1)
415 tm(5,4) = jacob(2,1)*jacob(3,2) + jacob(2,2)*jacob(3,1)
416 tm(6,4) = jacob(3,1)*jacob(1,2) + jacob(3,2)*jacob(1,1)
417 tm(4,5) = jacob(1,2)*jacob(2,3) + jacob(1,3)*jacob(2,2)
418 tm(5,5) = jacob(2,2)*jacob(3,3) + jacob(2,3)*jacob(3,2)
419 tm(6,5) = jacob(3,2)*jacob(1,3) + jacob(3,3)*jacob(1,2)
420 tm(4,6) = jacob(1,3)*jacob(2,1) + jacob(1,1)*jacob(2,3)
421 tm(5,6) = jacob(2,3)*jacob(3,1) + jacob(2,1)*jacob(3,3)
422 tm(6,6) = jacob(3,3)*jacob(1,1) + jacob(3,1)*jacob(1,3)
430 real(kind=kreal) :: tensor(1:6)
431 real(kind=kreal) :: eigval(3)
432 real(kind=kreal) :: princmatrix(3,3)
433 real(kind=kreal) :: princnormal(3,3)
434 real(kind=kreal) :: tempv(3)
435 real(kind=kreal) :: temps
437 call eigen3(tensor,eigval,princnormal)
439 if (eigval(1)<eigval(2))
then
443 tempv(:)=princnormal(:,1)
444 princnormal(:,1)=princnormal(:,2)
445 princnormal(:,2)=tempv(:)
447 if (eigval(1)<eigval(3))
then
451 tempv(:)=princnormal(:,1)
452 princnormal(:,1)=princnormal(:,3)
453 princnormal(:,3)=tempv(:)
455 if (eigval(2)<eigval(3))
then
459 tempv(:)=princnormal(:,2)
460 princnormal(:,2)=princnormal(:,3)
461 princnormal(:,3)=tempv(:)
466 princmatrix(i,j) = princnormal(i,j) * eigval(j)
475 real(kind=kreal) :: tensor(6)
476 real(kind=kreal) :: eigval(3)
477 real(kind=kreal) :: princ(3,3)
479 real(kind=kreal) :: s11, s22, s33, s12, s23, s13, j1, j2, j3
480 real(kind=kreal) :: ml,nl
481 complex(kind=kreal):: x1,x2,x3
482 real(kind=kreal):: rtemp
493 j2 = -s11*s22 - s22*s33 - s33*s11 + s12**2 + s23**2 + s13**2
494 j3 = s11*s22*s33 + 2*s12*s23*s13 - s11*s23**2 - s22*s13**2 - s33*s12**2
498 call cardano(-j1, -j2, -j3, x1, x2, x3)
502 if (eigval(1)<eigval(2))
then
507 if (eigval(1)<eigval(3))
then
512 if (eigval(2)<eigval(3))
then
519 if (eigval(i)/(eigval(1)+eigval(2)+eigval(3)) < 1.0d-10 )
then
524 ml = ( s23*s13 - s12*(s33-eigval(i)) ) / ( -s23**2 + (s22-eigval(i))*(s33-eigval(i)) )
525 nl = ( s12**2 - (s22-eigval(i))*(s11-eigval(i)) ) / ( s12*s23 - s13*(s22-eigval(i)) )
526 if (abs(ml) >= huge(ml))
then
529 if (abs(nl) >= huge(nl))
then
532 princ(i,1) = eigval(i)/sqrt( 1 + ml**2 + nl**2)
533 princ(i,2) = ml * princ(i,1)
534 princ(i,3) = nl * princ(i,1)
541 real(kind=kreal):: a,b,c
542 real(kind=kreal):: p,q,d
543 complex(kind=kreal):: w
544 complex(kind=kreal):: u,v,y
545 complex(kind=kreal):: x1,x2,x3
546 w = (-1.0d0 + sqrt(dcmplx(-3.0d0)))/2.0d0
547 p = -a**2/9.0d0 + b/3.0d0
548 q = 2.0d0/2.7d1*a**3 - a*b/3.0d0 + c
549 d = q**2 + 4.0d0*p**3
551 u = ((-dcmplx(q) + sqrt(dcmplx(d)))/2.0d0)**(1.0d0/3.0d0)
555 x1 = u + v -dcmplx(a)/3.0d0
556 x2 = u*w + v*w**2 -dcmplx(a)/3.0d0
557 x3 = u*w**2 + v*w -dcmplx(a)/3.0d0
559 y = (-dcmplx(q))**(1.0d0/3.0d0)
560 x1 = y -dcmplx(a)/3.0d0
561 x2 = y*w -dcmplx(a)/3.0d0
562 x3 = y*w**2 -dcmplx(a)/3.0d0
568 real(kind=kreal),
intent(in) :: r(3)
569 real(kind=kreal),
intent(inout) :: v(3)
571 real(kind=kreal) :: rotv(3), rv
572 real(kind=kreal) :: cosx, sinc(2)
573 real(kind=kreal) :: x, x2, x4, x6
574 real(kind=kreal),
parameter :: c0 = 0.5d0
575 real(kind=kreal),
parameter :: c2 = -4.166666666666666d-002
576 real(kind=kreal),
parameter :: c4 = 1.388888888888889d-003
577 real(kind=kreal),
parameter :: c6 = -2.480158730158730d-005
579 x2 = dot_product(r,r)
585 sinc(1) = 1.d0-x2/6.d0+x4/120.d0
586 sinc(2) = c0+c2*x2+c4*x4+c6*x6
589 sinc(2) = (1.d0-cosx)/x2
593 rv = dot_product(r,v)
594 rotv(1:3) = cosx*v(1:3)
595 rotv(1:3) = rotv(1:3)+rv*sinc(2)*r(1:3)
596 rotv(1) = rotv(1) + (-v(2)*r(3)+v(3)*r(2))*sinc(1)
597 rotv(2) = rotv(2) + (-v(3)*r(1)+v(1)*r(3))*sinc(1)
598 rotv(3) = rotv(3) + (-v(1)*r(2)+v(2)*r(1))*sinc(1)
605 real(kind=kreal),
intent(in) :: dpydpx(3,3)
606 real(kind=kreal),
intent(out) :: dydx(6,6)
607 real(kind=kreal),
intent(in) :: eigv(3,3)
608 real(kind=kreal),
intent(in) :: px(3), py(3)
610 real(kind=kreal) :: x(6)
611 real(kind=kreal) :: ep(6,3), dx2dx(6,6)
612 integer(kind=kint) :: i, j, m1, m2, m3, ia, ib, ic, ip, jp, k
613 real(kind=kreal) :: xmax, dif12, dif23, c1, c2, c3, c4, d1, d2, d3
614 real(kind=kreal) :: xa, xc, ya, yc, daa, dac, dca, dcb, dcc
615 real(kind=kreal) :: xa_xc, xa_xc2, xa_xc3, ya_yc, xc2
616 real(kind=kreal) :: s1, s2, s3, s4, s5, s6
617 real(kind=kreal),
parameter :: i2(6) = [1.d0, 1.d0, 1.d0, 0.d0, 0.d0, 0.d0]
618 real(kind=kreal),
parameter :: is(6,6) = reshape([&
619 1.d0, 0.d0, 0.d0, 0.d0, 0.d0, 0.d0,&
620 0.d0, 1.d0, 0.d0, 0.d0, 0.d0, 0.d0,&
621 0.d0, 0.d0, 1.d0, 0.d0, 0.d0, 0.d0,&
622 0.d0, 0.d0, 0.d0, 0.5d0, 0.d0, 0.d0,&
623 0.d0, 0.d0, 0.d0, 0.d0, 0.5d0, 0.d0,&
624 0.d0, 0.d0, 0.d0, 0.d0, 0.d0, 0.5d0],&
626 real(kind=kreal),
parameter :: eps=1.d-6
629 ep(1,i) = eigv(1,i)*eigv(1,i)
630 ep(2,i) = eigv(2,i)*eigv(2,i)
631 ep(3,i) = eigv(3,i)*eigv(3,i)
632 ep(4,i) = eigv(1,i)*eigv(2,i)
633 ep(5,i) = eigv(2,i)*eigv(3,i)
634 ep(6,i) = eigv(3,i)*eigv(1,i)
639 x(j) = x(j)+px(i)*ep(j,i)
642 dx2dx = reshape([2.d0*x(1), 0.d0, 0.d0, x(4), 0.d0, x(6),&
643 & 0.d0, 2.d0*x(2), 0.d0, x(4), x(5), 0.d0,&
644 & 0.d0, 0.d0, 2.d0*x(3), 0.d0, x(5), x(6),&
645 & x(4), x(4), 0.d0, (x(1)+x(2))/2.d0, x(6)/2.d0, x(5)/2.d0,&
646 & 0.d0, x(5), x(6), x(6)/2.d0, (x(2)+x(3))/2.d0, x(4)/2.d0,&
647 & x(6), 0.d0, x(6), x(5)/2.d0, x(4)/2.d0, (x(1)+x(3))/2.d0],&
652 m1 = 1; m2 = 2; m3 = 3
656 xmax = maxval(abs(px), 1)
657 if( xmax < eps ) xmax = 1.d0
658 dif12 = abs(px(m1) - px(m2)) / xmax
659 dif23 = abs(px(m2) - px(m3)) / xmax
660 if( dif12 < eps .and. dif23 < eps )
then
661 c1 = dpydpx(1,1)-dpydpx(1,2)
665 dydx(i,j) = c1*is(i,j)+c2*i2(i)*i2(j)
668 else if( dif12 < eps .or. dif23 < eps )
then
669 if( dif12 < eps )
then
670 ia = m3; ib = m1; ic = m2
672 ia = m1; ib = m2; ic = m3
674 ya = py(ia); yc = py(ic)
675 xa = px(ia); xc = px(ic)
683 xa_xc3 = xa_xc2*xa_xc
693 s1 = c1+(dcb-dcc)/xa_xc
694 s2 = 2.d0*xc*c1+(dcb-dcc)*c4
695 s3 = 2.d0*c2+d3/xa_xc2
696 s4 = 2.d0*xc*c2+(dac-dcb)/xa_xc+d3*c3
697 s5 = 2.d0*xc*c2+(dca-dcb)/xa_xc+d3*c3
698 s6 = 2.d0*xc2*c2+(d1*xa-d2*xc)*c3-dcb*c4
701 dydx(i,j) = s1*dx2dx(i,j)-s2*is(i,j)-s3*x(i)*x(j)+s4*x(i)*i2(j)+s5*i2(i)*x(j)-s6*i2(i)*i2(j)
709 ia = 1; ib = 2; ic = 3
711 ia = 2; ib = 3; ic = 1
713 ia = 3; ib = 1; ic = 2
715 c1 = py(ia)/((px(ia)-px(ib))*(px(ia)-px(ic)))
717 c3 = (px(ia)-px(ib))+(px(ia)-px(ic))
721 dydx(i,j) = dydx(i,j)+c1*(dx2dx(i,j)-c2*is(i,j)-c3*ep(i,ia)*ep(j,ia)-c4*(ep(i,ib)*ep(j,ib)-ep(i,ic)*ep(j,ic)))
730 dydx(i,j) = dydx(i,j)+c1*ep(i,ip)*ep(j,jp)
This module provides aux functions.
subroutine eigen3(tensor, eigval, princ)
Compute eigenvalue and eigenvetor for symmetric 3*3 tensor using Jacobi iteration adapted from numeri...
subroutine cross_product(v1, v2, vn)
subroutine eigen3d(tensor, eigval, princ)
real(kind=kreal) function determinant33(XJ)
Compute determinant for 3*3 matrix.
subroutine insert_int2array(iin, carray)
Insert an integer into a integer array.
real(kind=kreal) function determinant(mat)
Compute determinant for symmetric 3*3 matrix.
subroutine calsolve(NN, A, b)
Solve A x = b for dense NN x NN system (Gaussian elimination with partial pivoting)
subroutine tensor_eigen3(tensor, eigval)
Given symmetric 3x3 matrix M, compute the eigenvalues.
subroutine get_principal(tensor, eigval, princmatrix)
subroutine transformation(jacob, tm)
subroutine fstr_chk_alloc(imsg, sub_name, ierr)
subroutine deriv_general_iso_tensor_func_3d(dpydpx, dydx, eigv, px, py)
Compute derivative of a general isotropic tensor function of one tensor.
subroutine cardano(a, b, c, x1, x2, x3)
subroutine memget(var, dimn, syze)
Record used memory.
subroutine rotate_3dvector_by_rodrigues_formula(r, v)
subroutine calinverse(NN, A)
calculate inverse of matrix a