xref: /petsc/src/mat/utils/axpy.c (revision 2e8a6d31cfff42dc61c2443ddfa186a411c27ca7)
1a5eb4965SSatish Balay #ifdef PETSC_RCS_HEADER
2*2e8a6d31SBarry Smith static char vcid[] = "$Id: axpy.c,v 1.35 1998/07/06 03:11:22 bsmith Exp bsmith $";
36f79c3a4SBarry Smith #endif
46f79c3a4SBarry Smith 
570f55243SBarry Smith #include "src/mat/matimpl.h"  /*I   "mat.h"  I*/
66f79c3a4SBarry Smith 
75615d1e5SSatish Balay #undef __FUNC__
85615d1e5SSatish Balay #define __FUNC__ "MatAXPY"
906be10caSBarry Smith /*@
1021c89e3eSBarry Smith    MatAXPY - Computes Y = a*X + Y.
116f79c3a4SBarry Smith 
12fee21e36SBarry Smith    Collective on Mat
13fee21e36SBarry Smith 
1498a79cdbSBarry Smith    Input Parameters:
1598a79cdbSBarry Smith +  X,Y - the matrices
1698a79cdbSBarry Smith -  a - the scalar multiplier
1798a79cdbSBarry Smith 
18e182c471SBarry Smith    Contributed by: Matthew Knepley
19d4bb536fSBarry Smith 
209cf4f1e8SLois Curfman McInnes .keywords: matrix, add
21d4bb536fSBarry Smith 
2206be10caSBarry Smith  @*/
2306be10caSBarry Smith int MatAXPY(Scalar *a,Mat X,Mat Y)
246f79c3a4SBarry Smith {
2506be10caSBarry Smith   int    m1,m2,n1,n2,i,*row,start,end,j,ncols,ierr;
2606be10caSBarry Smith   Scalar *val,*vals;
276f79c3a4SBarry Smith 
283a40ed3dSBarry Smith   PetscFunctionBegin;
29d4bb536fSBarry Smith   PetscValidHeaderSpecific(X,MAT_COOKIE);
30d4bb536fSBarry Smith   PetscValidHeaderSpecific(Y,MAT_COOKIE);
3190f02eecSBarry Smith   PetscValidScalarPointer(a);
3290f02eecSBarry Smith 
33d4bb536fSBarry Smith   MatGetSize(X,&m1,&n1);  MatGetSize(Y,&m2,&n2);
34a8c6a408SBarry Smith   if (m1 != m2 || n1 != n2) SETERRQ(PETSC_ERR_ARG_SIZ,0,"Non conforming matrix add");
351987afe7SBarry Smith 
36f830108cSBarry Smith   if (X->ops->axpy) {
37f830108cSBarry Smith     ierr = (*X->ops->axpy)(a,X,Y); CHKERRQ(ierr);
38d4bb536fSBarry Smith   } else {
3990f02eecSBarry Smith     ierr = MatGetOwnershipRange(X,&start,&end); CHKERRQ(ierr);
40d4bb536fSBarry Smith     if (*a == 1.0) {
41d4bb536fSBarry Smith       for (i = start; i < end; i++) {
42d4bb536fSBarry Smith         ierr = MatGetRow(X, i, &ncols, &row, &vals);                 CHKERRQ(ierr);
43d4bb536fSBarry Smith         ierr = MatSetValues(Y, 1, &i, ncols, row, vals, ADD_VALUES); CHKERRQ(ierr);
44d4bb536fSBarry Smith         ierr = MatRestoreRow(X, i, &ncols, &row, &vals);             CHKERRQ(ierr);
45d4bb536fSBarry Smith       }
46d4bb536fSBarry Smith     } else {
47d4bb536fSBarry Smith       vals = (Scalar *) PetscMalloc( (n1+1)*sizeof(Scalar) ); CHKPTRQ(vals);
4806be10caSBarry Smith       for ( i=start; i<end; i++ ) {
4990f02eecSBarry Smith         ierr = MatGetRow(X,i,&ncols,&row,&val); CHKERRQ(ierr);
5006be10caSBarry Smith         for ( j=0; j<ncols; j++ ) {
5106be10caSBarry Smith           vals[j] = (*a)*val[j];
526f79c3a4SBarry Smith         }
53dbb450caSBarry Smith         ierr = MatSetValues(Y,1,&i,ncols,row,vals,ADD_VALUES); CHKERRQ(ierr);
5490f02eecSBarry Smith         ierr = MatRestoreRow(X,i,&ncols,&row,&val); CHKERRQ(ierr);
556f79c3a4SBarry Smith       }
560452661fSBarry Smith       PetscFree(vals);
57d4bb536fSBarry Smith     }
586d4a8577SBarry Smith     ierr = MatAssemblyBegin(Y,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
596d4a8577SBarry Smith     ierr = MatAssemblyEnd(Y,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
601987afe7SBarry Smith   }
613a40ed3dSBarry Smith   PetscFunctionReturn(0);
626f79c3a4SBarry Smith }
63052efed2SBarry Smith 
645615d1e5SSatish Balay #undef __FUNC__
655615d1e5SSatish Balay #define __FUNC__ "MatShift"
66052efed2SBarry Smith /*@
676b9ee512SLois Curfman McInnes    MatShift - Computes Y =  Y + a I, where a is a scalar and I is the identity
686b9ee512SLois Curfman McInnes    matrix.
69052efed2SBarry Smith 
70fee21e36SBarry Smith    Collective on Mat
71fee21e36SBarry Smith 
7298a79cdbSBarry Smith    Input Parameters:
7398a79cdbSBarry Smith +  Y - the matrices
7498a79cdbSBarry Smith -  a - the scalar
7598a79cdbSBarry Smith 
76052efed2SBarry Smith .keywords: matrix, add, shift
776b9ee512SLois Curfman McInnes 
786b9ee512SLois Curfman McInnes .seealso: MatDiagonalShift()
79052efed2SBarry Smith  @*/
80052efed2SBarry Smith int MatShift(Scalar *a,Mat Y)
81052efed2SBarry Smith {
82052efed2SBarry Smith   int    i,start,end,ierr;
83052efed2SBarry Smith 
843a40ed3dSBarry Smith   PetscFunctionBegin;
8577c4ece6SBarry Smith   PetscValidHeaderSpecific(Y,MAT_COOKIE);
8690f02eecSBarry Smith   PetscValidScalarPointer(a);
87f830108cSBarry Smith   if (Y->ops->shift) {
88f830108cSBarry Smith     ierr = (*Y->ops->shift)(a,Y); CHKERRQ(ierr);
8962d58ce1SBarry Smith   } else {
90d4bb536fSBarry Smith     ierr = MatGetOwnershipRange(Y,&start,&end); CHKERRQ(ierr);
91052efed2SBarry Smith     for ( i=start; i<end; i++ ) {
92052efed2SBarry Smith       ierr = MatSetValues(Y,1,&i,1,&i,a,ADD_VALUES); CHKERRQ(ierr);
93052efed2SBarry Smith     }
946d4a8577SBarry Smith     ierr = MatAssemblyBegin(Y,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
956d4a8577SBarry Smith     ierr = MatAssemblyEnd(Y,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
96052efed2SBarry Smith   }
973a40ed3dSBarry Smith   PetscFunctionReturn(0);
98052efed2SBarry Smith }
996d84be18SBarry Smith 
1005615d1e5SSatish Balay #undef __FUNC__
1015615d1e5SSatish Balay #define __FUNC__ "MatDiagonalShift"
1026d84be18SBarry Smith /*@
1036b9ee512SLois Curfman McInnes    MatDiagonalShift - Computes Y = Y + D, where D is a diagonal matrix
1046b9ee512SLois Curfman McInnes    that is represented as a vector.
1056d84be18SBarry Smith 
1066d84be18SBarry Smith    Input Parameters:
10798a79cdbSBarry Smith +  Y - the input matrix
10898a79cdbSBarry Smith -  D - the diagonal matrix, represented as a vector
1096d84be18SBarry Smith 
1106b9ee512SLois Curfman McInnes    Input Parameters:
1116b9ee512SLois Curfman McInnes .  Y - the shifted ouput matrix
1126d84be18SBarry Smith 
113fee21e36SBarry Smith    Collective on Mat and Vec
114fee21e36SBarry Smith 
1156b9ee512SLois Curfman McInnes .keywords: matrix, add, shift, diagonal
1166b9ee512SLois Curfman McInnes 
1176b9ee512SLois Curfman McInnes .seealso: MatShift()
1186d84be18SBarry Smith @*/
1196d84be18SBarry Smith int MatDiagonalShift(Mat Y,Vec D)
1206d84be18SBarry Smith {
1216d84be18SBarry Smith   int    i,start,end,ierr;
1226d84be18SBarry Smith 
1233a40ed3dSBarry Smith   PetscFunctionBegin;
12477c4ece6SBarry Smith   PetscValidHeaderSpecific(Y,MAT_COOKIE);
12590f02eecSBarry Smith   PetscValidHeaderSpecific(D,VEC_COOKIE);
126f830108cSBarry Smith   if (Y->ops->shift) {
127f830108cSBarry Smith     ierr = (*Y->ops->diagonalshift)(D,Y); CHKERRQ(ierr);
12894d884c6SBarry Smith   } else {
1296d84be18SBarry Smith     int    vstart,vend;
1306d84be18SBarry Smith     Scalar *v;
1316d84be18SBarry Smith     ierr = VecGetOwnershipRange(D,&vstart,&vend); CHKERRQ(ierr);
1326d84be18SBarry Smith     ierr = MatGetOwnershipRange(Y,&start,&end); CHKERRQ(ierr);
133d4bb536fSBarry Smith     if (vstart != start || vend != end) {
134a8c6a408SBarry Smith       SETERRQ(PETSC_ERR_ARG_SIZ,0,"Vector ownership range not compatible with matrix");
135d4bb536fSBarry Smith     }
1366d84be18SBarry Smith 
1376d84be18SBarry Smith     ierr = VecGetArray(D,&v); CHKERRQ(ierr);
1386d84be18SBarry Smith     for ( i=start; i<end; i++ ) {
1396d84be18SBarry Smith       ierr = MatSetValues(Y,1,&i,1,&i,v+i-start,ADD_VALUES); CHKERRQ(ierr);
1406d84be18SBarry Smith     }
141*2e8a6d31SBarry Smith     ierr = VecRestoreArray(D,&v); CHKERRQ(ierr);
1426d4a8577SBarry Smith     ierr = MatAssemblyBegin(Y,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
1436d4a8577SBarry Smith     ierr = MatAssemblyEnd(Y,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
1446d84be18SBarry Smith   }
1453a40ed3dSBarry Smith   PetscFunctionReturn(0);
1466d84be18SBarry Smith }
147d4bb536fSBarry Smith 
148d4bb536fSBarry Smith #undef __FUNC__
149d4bb536fSBarry Smith #define __FUNC__ "MatAYPX"
150d4bb536fSBarry Smith /*@
151d4bb536fSBarry Smith    MatAYPX - Computes Y = X + a*Y.
152d4bb536fSBarry Smith 
153fee21e36SBarry Smith    Collective on Mat
154fee21e36SBarry Smith 
15598a79cdbSBarry Smith    Input Parameters:
15698a79cdbSBarry Smith +  X,Y - the matrices
15798a79cdbSBarry Smith -  a - the scalar multiplier
15898a79cdbSBarry Smith 
159e182c471SBarry Smith    Contributed by: Matthew Knepley
160d4bb536fSBarry Smith 
161d4bb536fSBarry Smith .keywords: matrix, add
162d4bb536fSBarry Smith 
163d4bb536fSBarry Smith  @*/
164d4bb536fSBarry Smith int MatAYPX(Scalar *a,Mat X,Mat Y)
165d4bb536fSBarry Smith {
166d4bb536fSBarry Smith   Scalar one = 1.0;
167d4bb536fSBarry Smith   int    mX, mY,nX, nY,ierr;
168d4bb536fSBarry Smith 
1693a40ed3dSBarry Smith   PetscFunctionBegin;
170d4bb536fSBarry Smith   PetscValidHeaderSpecific(X, MAT_COOKIE);
171d4bb536fSBarry Smith   PetscValidHeaderSpecific(Y, MAT_COOKIE);
172d4bb536fSBarry Smith   PetscValidScalarPointer(a);
173d4bb536fSBarry Smith 
174d4bb536fSBarry Smith   MatGetSize(X, &mX, &nX);
175d4bb536fSBarry Smith   MatGetSize(X, &mY, &nY);
176a8c6a408SBarry Smith   if (mX != mY || nX != nY) SETERRQ(PETSC_ERR_ARG_SIZ,0,"Non conforming matrices");
177d4bb536fSBarry Smith 
178d4bb536fSBarry Smith   ierr = MatScale(a, Y);      CHKERRQ(ierr);
179d4bb536fSBarry Smith   ierr = MatAXPY(&one, X, Y); CHKERRQ(ierr);
1803a40ed3dSBarry Smith   PetscFunctionReturn(0);
181d4bb536fSBarry Smith }
182