Actual source code: matrix.c
2: /*
3: This is where the abstract matrix operations are defined
4: */
6: #include src/mat/matimpl.h
7: #include vecimpl.h
9: /* Logging support */
10: PetscCookie MAT_COOKIE = 0, MATSNESMFCTX_COOKIE = 0;
11: PetscEvent MAT_Mult = 0, MAT_MultMatrixFree = 0, MAT_Mults = 0, MAT_MultConstrained = 0, MAT_MultAdd = 0, MAT_MultTranspose = 0;
12: PetscEvent MAT_MultTransposeConstrained = 0, MAT_MultTransposeAdd = 0, MAT_Solve = 0, MAT_Solves = 0, MAT_SolveAdd = 0, MAT_SolveTranspose = 0;
13: PetscEvent MAT_SolveTransposeAdd = 0, MAT_Relax = 0, MAT_ForwardSolve = 0, MAT_BackwardSolve = 0, MAT_LUFactor = 0, MAT_LUFactorSymbolic = 0;
14: PetscEvent MAT_LUFactorNumeric = 0, MAT_CholeskyFactor = 0, MAT_CholeskyFactorSymbolic = 0, MAT_CholeskyFactorNumeric = 0, MAT_ILUFactor = 0;
15: PetscEvent MAT_ILUFactorSymbolic = 0, MAT_ICCFactorSymbolic = 0, MAT_Copy = 0, MAT_Convert = 0, MAT_Scale = 0, MAT_AssemblyBegin = 0;
16: PetscEvent MAT_AssemblyEnd = 0, MAT_SetValues = 0, MAT_GetValues = 0, MAT_GetRow = 0, MAT_GetSubMatrices = 0, MAT_GetColoring = 0, MAT_GetOrdering = 0;
17: PetscEvent MAT_IncreaseOverlap = 0, MAT_Partitioning = 0, MAT_ZeroEntries = 0, MAT_Load = 0, MAT_View = 0, MAT_AXPY = 0, MAT_FDColoringCreate = 0;
18: PetscEvent MAT_FDColoringApply = 0,MAT_Transpose = 0,MAT_FDColoringFunction = 0;
19: PetscEvent MAT_MatMult = 0, MAT_MatMultSymbolic = 0, MAT_MatMultNumeric = 0;
20: PetscEvent MAT_PtAP = 0, MAT_PtAPSymbolic = 0, MAT_PtAPNumeric = 0;
21: PetscEvent MAT_MatMultTranspose = 0, MAT_MatMultTransposeSymbolic = 0, MAT_MatMultTransposeNumeric = 0;
23: /* nasty global values for MatSetValue() */
24: PetscInt MatSetValue_Row = 0, MatSetValue_Column = 0;
25: PetscScalar MatSetValue_Value = 0.0;
29: /*@C
30: MatGetRow - Gets a row of a matrix. You MUST call MatRestoreRow()
31: for each row that you get to ensure that your application does
32: not bleed memory.
34: Not Collective
36: Input Parameters:
37: + mat - the matrix
38: - row - the row to get
40: Output Parameters:
41: + ncols - if not NULL, the number of nonzeros in the row
42: . cols - if not NULL, the column numbers
43: - vals - if not NULL, the values
45: Notes:
46: This routine is provided for people who need to have direct access
47: to the structure of a matrix. We hope that we provide enough
48: high-level matrix routines that few users will need it.
50: MatGetRow() always returns 0-based column indices, regardless of
51: whether the internal representation is 0-based (default) or 1-based.
53: For better efficiency, set cols and/or vals to PETSC_NULL if you do
54: not wish to extract these quantities.
56: The user can only examine the values extracted with MatGetRow();
57: the values cannot be altered. To change the matrix entries, one
58: must use MatSetValues().
60: You can only have one call to MatGetRow() outstanding for a particular
61: matrix at a time, per processor. MatGetRow() can only obtained rows
62: associated with the given processor, it cannot get rows from the
63: other processors; for that we suggest using MatGetSubMatrices(), then
64: MatGetRow() on the submatrix. The row indix passed to MatGetRows()
65: is in the global number of rows.
67: Fortran Notes:
68: The calling sequence from Fortran is
69: .vb
70: MatGetRow(matrix,row,ncols,cols,values,ierr)
71: Mat matrix (input)
72: integer row (input)
73: integer ncols (output)
74: integer cols(maxcols) (output)
75: double precision (or double complex) values(maxcols) output
76: .ve
77: where maxcols >= maximum nonzeros in any row of the matrix.
80: Caution:
81: Do not try to change the contents of the output arrays (cols and vals).
82: In some cases, this may corrupt the matrix.
84: Level: advanced
86: Concepts: matrices^row access
88: .seealso: MatRestoreRow(), MatSetValues(), MatGetValues(), MatGetSubmatrices(), MatGetDiagonal()
89: @*/
91: PetscErrorCode MatGetRow(Mat mat,PetscInt row,PetscInt *ncols,const PetscInt *cols[],const PetscScalar *vals[])
92: {
94: PetscInt incols;
99: MatPreallocated(mat);
100: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
101: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
102: if (!mat->ops->getrow) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
103: PetscLogEventBegin(MAT_GetRow,mat,0,0,0);
104: (*mat->ops->getrow)(mat,row,&incols,(PetscInt **)cols,(PetscScalar **)vals);
105: if (ncols) *ncols = incols;
106: PetscLogEventEnd(MAT_GetRow,mat,0,0,0);
107: return(0);
108: }
112: /*@C
113: MatRestoreRow - Frees any temporary space allocated by MatGetRow().
115: Not Collective
117: Input Parameters:
118: + mat - the matrix
119: . row - the row to get
120: . ncols, cols - the number of nonzeros and their columns
121: - vals - if nonzero the column values
123: Notes:
124: This routine should be called after you have finished examining the entries.
126: Fortran Notes:
127: The calling sequence from Fortran is
128: .vb
129: MatRestoreRow(matrix,row,ncols,cols,values,ierr)
130: Mat matrix (input)
131: integer row (input)
132: integer ncols (output)
133: integer cols(maxcols) (output)
134: double precision (or double complex) values(maxcols) output
135: .ve
136: Where maxcols >= maximum nonzeros in any row of the matrix.
138: In Fortran MatRestoreRow() MUST be called after MatGetRow()
139: before another call to MatGetRow() can be made.
141: Level: advanced
143: .seealso: MatGetRow()
144: @*/
145: PetscErrorCode MatRestoreRow(Mat mat,PetscInt row,PetscInt *ncols,const PetscInt *cols[],const PetscScalar *vals[])
146: {
152: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
153: if (!mat->ops->restorerow) return(0);
154: (*mat->ops->restorerow)(mat,row,ncols,(PetscInt **)cols,(PetscScalar **)vals);
155: return(0);
156: }
160: /*@C
161: MatView - Visualizes a matrix object.
163: Collective on Mat
165: Input Parameters:
166: + mat - the matrix
167: - viewer - visualization context
169: Notes:
170: The available visualization contexts include
171: + PETSC_VIEWER_STDOUT_SELF - standard output (default)
172: . PETSC_VIEWER_STDOUT_WORLD - synchronized standard
173: output where only the first processor opens
174: the file. All other processors send their
175: data to the first processor to print.
176: - PETSC_VIEWER_DRAW_WORLD - graphical display of nonzero structure
178: The user can open alternative visualization contexts with
179: + PetscViewerASCIIOpen() - Outputs matrix to a specified file
180: . PetscViewerBinaryOpen() - Outputs matrix in binary to a
181: specified file; corresponding input uses MatLoad()
182: . PetscViewerDrawOpen() - Outputs nonzero matrix structure to
183: an X window display
184: - PetscViewerSocketOpen() - Outputs matrix to Socket viewer.
185: Currently only the sequential dense and AIJ
186: matrix types support the Socket viewer.
188: The user can call PetscViewerSetFormat() to specify the output
189: format of ASCII printed objects (when using PETSC_VIEWER_STDOUT_SELF,
190: PETSC_VIEWER_STDOUT_WORLD and PetscViewerASCIIOpen). Available formats include
191: + PETSC_VIEWER_ASCII_DEFAULT - default, prints matrix contents
192: . PETSC_VIEWER_ASCII_MATLAB - prints matrix contents in Matlab format
193: . PETSC_VIEWER_ASCII_DENSE - prints entire matrix including zeros
194: . PETSC_VIEWER_ASCII_COMMON - prints matrix contents, using a sparse
195: format common among all matrix types
196: . PETSC_VIEWER_ASCII_IMPL - prints matrix contents, using an implementation-specific
197: format (which is in many cases the same as the default)
198: . PETSC_VIEWER_ASCII_INFO - prints basic information about the matrix
199: size and structure (not the matrix entries)
200: . PETSC_VIEWER_ASCII_INFO_DETAIL - prints more detailed information about
201: the matrix structure
203: Options Database Keys:
204: + -mat_view_info - Prints info on matrix at conclusion of MatEndAssembly()
205: . -mat_view_info_detailed - Prints more detailed info
206: . -mat_view - Prints matrix in ASCII format
207: . -mat_view_matlab - Prints matrix in Matlab format
208: . -mat_view_draw - PetscDraws nonzero structure of matrix, using MatView() and PetscDrawOpenX().
209: . -display <name> - Sets display name (default is host)
210: . -draw_pause <sec> - Sets number of seconds to pause after display
211: . -mat_view_socket - Sends matrix to socket, can be accessed from Matlab (see users manual)
212: . -viewer_socket_machine <machine>
213: . -viewer_socket_port <port>
214: . -mat_view_binary - save matrix to file in binary format
215: - -viewer_binary_filename <name>
216: Level: beginner
218: Concepts: matrices^viewing
219: Concepts: matrices^plotting
220: Concepts: matrices^printing
222: .seealso: PetscViewerSetFormat(), PetscViewerASCIIOpen(), PetscViewerDrawOpen(),
223: PetscViewerSocketOpen(), PetscViewerBinaryOpen(), MatLoad()
224: @*/
225: PetscErrorCode MatView(Mat mat,PetscViewer viewer)
226: {
227: PetscErrorCode ierr;
228: PetscInt rows,cols;
229: PetscTruth iascii;
230: char *cstr;
231: PetscViewerFormat format;
236: MatPreallocated(mat);
237: if (!viewer) viewer = PETSC_VIEWER_STDOUT_(mat->comm);
240: if (!mat->assembled) SETERRQ(PETSC_ERR_ORDER,"Must call MatAssemblyBegin/End() before viewing matrix");
242: PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&iascii);
243: if (iascii) {
244: PetscViewerGetFormat(viewer,&format);
245: if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_DETAIL) {
246: if (mat->prefix) {
247: PetscViewerASCIIPrintf(viewer,"Matrix Object:(%s)\n",mat->prefix);
248: } else {
249: PetscViewerASCIIPrintf(viewer,"Matrix Object:\n");
250: }
251: PetscViewerASCIIPushTab(viewer);
252: MatGetType(mat,&cstr);
253: MatGetSize(mat,&rows,&cols);
254: PetscViewerASCIIPrintf(viewer,"type=%s, rows=%D, cols=%D\n",cstr,rows,cols);
255: if (mat->ops->getinfo) {
256: MatInfo info;
257: MatGetInfo(mat,MAT_GLOBAL_SUM,&info);
258: PetscViewerASCIIPrintf(viewer,"total: nonzeros=%D, allocated nonzeros=%D\n",
259: (PetscInt)info.nz_used,(PetscInt)info.nz_allocated);
260: }
261: }
262: }
263: if (mat->ops->view) {
264: PetscViewerASCIIPushTab(viewer);
265: (*mat->ops->view)(mat,viewer);
266: PetscViewerASCIIPopTab(viewer);
267: } else if (!iascii) {
268: SETERRQ1(PETSC_ERR_SUP,"Viewer type %s not supported",((PetscObject)viewer)->type_name);
269: }
270: if (iascii) {
271: PetscViewerGetFormat(viewer,&format);
272: if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_DETAIL) {
273: PetscViewerASCIIPopTab(viewer);
274: }
275: }
276: return(0);
277: }
281: /*@C
282: MatScaleSystem - Scale a vector solution and right hand side to
283: match the scaling of a scaled matrix.
284:
285: Collective on Mat
287: Input Parameter:
288: + mat - the matrix
289: . x - solution vector (or PETSC_NULL)
290: - b - right hand side vector (or PETSC_NULL)
293: Notes:
294: For AIJ, BAIJ, and BDiag matrix formats, the matrices are not
295: internally scaled, so this does nothing. For MPIROWBS it
296: permutes and diagonally scales.
298: The KSP methods automatically call this routine when required
299: (via PCPreSolve()) so it is rarely used directly.
301: Level: Developer
303: Concepts: matrices^scaling
305: .seealso: MatUseScaledForm(), MatUnScaleSystem()
306: @*/
307: PetscErrorCode MatScaleSystem(Mat mat,Vec x,Vec b)
308: {
314: MatPreallocated(mat);
318: if (mat->ops->scalesystem) {
319: (*mat->ops->scalesystem)(mat,x,b);
320: }
321: return(0);
322: }
326: /*@C
327: MatUnScaleSystem - Unscales a vector solution and right hand side to
328: match the original scaling of a scaled matrix.
329:
330: Collective on Mat
332: Input Parameter:
333: + mat - the matrix
334: . x - solution vector (or PETSC_NULL)
335: - b - right hand side vector (or PETSC_NULL)
338: Notes:
339: For AIJ, BAIJ, and BDiag matrix formats, the matrices are not
340: internally scaled, so this does nothing. For MPIROWBS it
341: permutes and diagonally scales.
343: The KSP methods automatically call this routine when required
344: (via PCPreSolve()) so it is rarely used directly.
346: Level: Developer
348: .seealso: MatUseScaledForm(), MatScaleSystem()
349: @*/
350: PetscErrorCode MatUnScaleSystem(Mat mat,Vec x,Vec b)
351: {
357: MatPreallocated(mat);
360: if (mat->ops->unscalesystem) {
361: (*mat->ops->unscalesystem)(mat,x,b);
362: }
363: return(0);
364: }
368: /*@C
369: MatUseScaledForm - For matrix storage formats that scale the
370: matrix (for example MPIRowBS matrices are diagonally scaled on
371: assembly) indicates matrix operations (MatMult() etc) are
372: applied using the scaled matrix.
373:
374: Collective on Mat
376: Input Parameter:
377: + mat - the matrix
378: - scaled - PETSC_TRUE for applying the scaled, PETSC_FALSE for
379: applying the original matrix
381: Notes:
382: For scaled matrix formats, applying the original, unscaled matrix
383: will be slightly more expensive
385: Level: Developer
387: .seealso: MatScaleSystem(), MatUnScaleSystem()
388: @*/
389: PetscErrorCode MatUseScaledForm(Mat mat,PetscTruth scaled)
390: {
396: MatPreallocated(mat);
397: if (mat->ops->usescaledform) {
398: (*mat->ops->usescaledform)(mat,scaled);
399: }
400: return(0);
401: }
405: /*@C
406: MatDestroy - Frees space taken by a matrix.
407:
408: Collective on Mat
410: Input Parameter:
411: . A - the matrix
413: Level: beginner
415: @*/
416: PetscErrorCode MatDestroy(Mat A)
417: {
423: MatPreallocated(A);
424: if (--A->refct > 0) return(0);
426: /* if memory was published with AMS then destroy it */
427: PetscObjectDepublish(A);
428: if (A->mapping) {
429: ISLocalToGlobalMappingDestroy(A->mapping);
430: }
431: if (A->bmapping) {
432: ISLocalToGlobalMappingDestroy(A->bmapping);
433: }
434: if (A->rmap) {
435: PetscMapDestroy(A->rmap);
436: }
437: if (A->cmap) {
438: PetscMapDestroy(A->cmap);
439: }
441: (*A->ops->destroy)(A);
442: PetscLogObjectDestroy(A);
443: PetscHeaderDestroy(A);
444: return(0);
445: }
449: /*@
450: MatValid - Checks whether a matrix object is valid.
452: Collective on Mat
454: Input Parameter:
455: . m - the matrix to check
457: Output Parameter:
458: flg - flag indicating matrix status, either
459: PETSC_TRUE if matrix is valid, or PETSC_FALSE otherwise.
461: Level: developer
463: Concepts: matrices^validity
464: @*/
465: PetscErrorCode MatValid(Mat m,PetscTruth *flg)
466: {
469: if (!m) *flg = PETSC_FALSE;
470: else if (m->cookie != MAT_COOKIE) *flg = PETSC_FALSE;
471: else *flg = PETSC_TRUE;
472: return(0);
473: }
477: /*@
478: MatSetValues - Inserts or adds a block of values into a matrix.
479: These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
480: MUST be called after all calls to MatSetValues() have been completed.
482: Not Collective
484: Input Parameters:
485: + mat - the matrix
486: . v - a logically two-dimensional array of values
487: . m, idxm - the number of rows and their global indices
488: . n, idxn - the number of columns and their global indices
489: - addv - either ADD_VALUES or INSERT_VALUES, where
490: ADD_VALUES adds values to any existing entries, and
491: INSERT_VALUES replaces existing entries with new values
493: Notes:
494: By default the values, v, are row-oriented and unsorted.
495: See MatSetOption() for other options.
497: Calls to MatSetValues() with the INSERT_VALUES and ADD_VALUES
498: options cannot be mixed without intervening calls to the assembly
499: routines.
501: MatSetValues() uses 0-based row and column numbers in Fortran
502: as well as in C.
504: Negative indices may be passed in idxm and idxn, these rows and columns are
505: simply ignored. This allows easily inserting element stiffness matrices
506: with homogeneous Dirchlet boundary conditions that you don't want represented
507: in the matrix.
509: Efficiency Alert:
510: The routine MatSetValuesBlocked() may offer much better efficiency
511: for users of block sparse formats (MATSEQBAIJ and MATMPIBAIJ).
513: Level: beginner
515: Concepts: matrices^putting entries in
517: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
518: InsertMode, INSERT_VALUES, ADD_VALUES
519: @*/
520: PetscErrorCode MatSetValues(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],const PetscScalar v[],InsertMode addv)
521: {
525: if (!m || !n) return(0); /* no values to insert */
528: MatPreallocated(mat);
532: if (mat->insertmode == NOT_SET_VALUES) {
533: mat->insertmode = addv;
534: }
535: #if defined(PETSC_USE_BOPT_g)
536: else if (mat->insertmode != addv) {
537: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
538: }
539: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
540: #endif
542: if (mat->assembled) {
543: mat->was_assembled = PETSC_TRUE;
544: mat->assembled = PETSC_FALSE;
545: }
546: PetscLogEventBegin(MAT_SetValues,mat,0,0,0);
547: if (!mat->ops->setvalues) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
548: (*mat->ops->setvalues)(mat,m,idxm,n,idxn,v,addv);
549: PetscLogEventEnd(MAT_SetValues,mat,0,0,0);
550: return(0);
551: }
555: /*@C
556: MatSetValuesStencil - Inserts or adds a block of values into a matrix.
557: Using structured grid indexing
559: Not Collective
561: Input Parameters:
562: + mat - the matrix
563: . v - a logically two-dimensional array of values
564: . m - number of rows being entered
565: . idxm - grid coordinates (and component number when dof > 1) for matrix rows being entered
566: . n - number of columns being entered
567: . idxn - grid coordinates (and component number when dof > 1) for matrix columns being entered
568: - addv - either ADD_VALUES or INSERT_VALUES, where
569: ADD_VALUES adds values to any existing entries, and
570: INSERT_VALUES replaces existing entries with new values
572: Notes:
573: By default the values, v, are row-oriented and unsorted.
574: See MatSetOption() for other options.
576: Calls to MatSetValuesStencil() with the INSERT_VALUES and ADD_VALUES
577: options cannot be mixed without intervening calls to the assembly
578: routines.
580: The grid coordinates are across the entire grid, not just the local portion
582: MatSetValuesStencil() uses 0-based row and column numbers in Fortran
583: as well as in C.
585: For setting/accessing vector values via array coordinates you can use the DAVecGetArray() routine
587: In order to use this routine you must either obtain the matrix with DAGetMatrix()
588: or call MatSetLocalToGlobalMapping() and MatSetStencil() first.
590: The columns and rows in the stencil passed in MUST be contained within the
591: ghost region of the given process as set with DACreateXXX() or MatSetStencil(). For example,
592: if you create a DA with an overlap of one grid level and on a particular process its first
593: local nonghost x logical coordinate is 6 (so its first ghost x logical coordinate is 5) the
594: first i index you can use in your column and row indices in MatSetStencil() is 5.
596: In Fortran idxm and idxn should be declared as
597: $ MatStencil idxm(4,m),idxn(4,n)
598: and the values inserted using
599: $ idxm(MatStencil_i,1) = i
600: $ idxm(MatStencil_j,1) = j
601: $ idxm(MatStencil_k,1) = k
602: $ idxm(MatStencil_c,1) = c
603: etc
605: Negative indices may be passed in idxm and idxn, these rows and columns are
606: simply ignored. This allows easily inserting element stiffness matrices
607: with homogeneous Dirchlet boundary conditions that you don't want represented
608: in the matrix.
610: Inspired by the structured grid interface to the HYPRE package
611: (http://www.llnl.gov/CASC/hypre)
613: Efficiency Alert:
614: The routine MatSetValuesBlockedStencil() may offer much better efficiency
615: for users of block sparse formats (MATSEQBAIJ and MATMPIBAIJ).
617: Level: beginner
619: Concepts: matrices^putting entries in
621: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal()
622: MatSetValues(), MatSetValuesBlockedStencil(), MatSetStencil(), DAGetMatrix(), DAVecGetArray(), MatStencil
623: @*/
624: PetscErrorCode MatSetValuesStencil(Mat mat,PetscInt m,const MatStencil idxm[],PetscInt n,const MatStencil idxn[],const PetscScalar v[],InsertMode addv)
625: {
627: PetscInt j,i,jdxm[128],jdxn[256],dim = mat->stencil.dim,*dims = mat->stencil.dims+1,tmp;
628: PetscInt *starts = mat->stencil.starts,*dxm = (PetscInt*)idxm,*dxn = (PetscInt*)idxn,sdim = dim - (1 - (PetscInt)mat->stencil.noc);
631: if (!m || !n) return(0); /* no values to insert */
638: if (m > 128) SETERRQ1(PETSC_ERR_SUP,"Can only set 128 rows at a time; trying to set %D",m);
639: if (n > 128) SETERRQ1(PETSC_ERR_SUP,"Can only set 256 columns at a time; trying to set %D",n);
641: for (i=0; i<m; i++) {
642: for (j=0; j<3-sdim; j++) dxm++;
643: tmp = *dxm++ - starts[0];
644: for (j=0; j<dim-1; j++) {
645: if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
646: else tmp = tmp*dims[j] + dxm[-1] - starts[j+1];
647: }
648: if (mat->stencil.noc) dxm++;
649: jdxm[i] = tmp;
650: }
651: for (i=0; i<n; i++) {
652: for (j=0; j<3-sdim; j++) dxn++;
653: tmp = *dxn++ - starts[0];
654: for (j=0; j<dim-1; j++) {
655: if ((*dxn++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
656: else tmp = tmp*dims[j] + dxn[-1] - starts[j+1];
657: }
658: if (mat->stencil.noc) dxn++;
659: jdxn[i] = tmp;
660: }
661: MatSetValuesLocal(mat,m,jdxm,n,jdxn,v,addv);
662: return(0);
663: }
667: /*@C
668: MatSetValuesBlockedStencil - Inserts or adds a block of values into a matrix.
669: Using structured grid indexing
671: Not Collective
673: Input Parameters:
674: + mat - the matrix
675: . v - a logically two-dimensional array of values
676: . m - number of rows being entered
677: . idxm - grid coordinates for matrix rows being entered
678: . n - number of columns being entered
679: . idxn - grid coordinates for matrix columns being entered
680: - addv - either ADD_VALUES or INSERT_VALUES, where
681: ADD_VALUES adds values to any existing entries, and
682: INSERT_VALUES replaces existing entries with new values
684: Notes:
685: By default the values, v, are row-oriented and unsorted.
686: See MatSetOption() for other options.
688: Calls to MatSetValuesBlockedStencil() with the INSERT_VALUES and ADD_VALUES
689: options cannot be mixed without intervening calls to the assembly
690: routines.
692: The grid coordinates are across the entire grid, not just the local portion
694: MatSetValuesBlockedStencil() uses 0-based row and column numbers in Fortran
695: as well as in C.
697: For setting/accessing vector values via array coordinates you can use the DAVecGetArray() routine
699: In order to use this routine you must either obtain the matrix with DAGetMatrix()
700: or call MatSetLocalToGlobalMapping() and MatSetStencil() first.
702: The columns and rows in the stencil passed in MUST be contained within the
703: ghost region of the given process as set with DACreateXXX() or MatSetStencil(). For example,
704: if you create a DA with an overlap of one grid level and on a particular process its first
705: local nonghost x logical coordinate is 6 (so its first ghost x logical coordinate is 5) the
706: first i index you can use in your column and row indices in MatSetStencil() is 5.
708: In Fortran idxm and idxn should be declared as
709: $ MatStencil idxm(4,m),idxn(4,n)
710: and the values inserted using
711: $ idxm(MatStencil_i,1) = i
712: $ idxm(MatStencil_j,1) = j
713: $ idxm(MatStencil_k,1) = k
714: etc
716: Negative indices may be passed in idxm and idxn, these rows and columns are
717: simply ignored. This allows easily inserting element stiffness matrices
718: with homogeneous Dirchlet boundary conditions that you don't want represented
719: in the matrix.
721: Inspired by the structured grid interface to the HYPRE package
722: (http://www.llnl.gov/CASC/hypre)
724: Level: beginner
726: Concepts: matrices^putting entries in
728: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal()
729: MatSetValues(), MatSetValuesStencil(), MatSetStencil(), DAGetMatrix(), DAVecGetArray(), MatStencil
730: @*/
731: PetscErrorCode MatSetValuesBlockedStencil(Mat mat,PetscInt m,const MatStencil idxm[],PetscInt n,const MatStencil idxn[],const PetscScalar v[],InsertMode addv)
732: {
734: PetscInt j,i,jdxm[128],jdxn[256],dim = mat->stencil.dim,*dims = mat->stencil.dims+1,tmp;
735: PetscInt *starts = mat->stencil.starts,*dxm = (PetscInt*)idxm,*dxn = (PetscInt*)idxn,sdim = dim - (1 - (PetscInt)mat->stencil.noc);
738: if (!m || !n) return(0); /* no values to insert */
745: if (m > 128) SETERRQ1(PETSC_ERR_SUP,"Can only set 128 rows at a time; trying to set %D",m);
746: if (n > 128) SETERRQ1(PETSC_ERR_SUP,"Can only set 256 columns at a time; trying to set %D",n);
748: for (i=0; i<m; i++) {
749: for (j=0; j<3-sdim; j++) dxm++;
750: tmp = *dxm++ - starts[0];
751: for (j=0; j<sdim-1; j++) {
752: if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
753: else tmp = tmp*dims[j] + dxm[-1] - starts[j+1];
754: }
755: dxm++;
756: jdxm[i] = tmp;
757: }
758: for (i=0; i<n; i++) {
759: for (j=0; j<3-sdim; j++) dxn++;
760: tmp = *dxn++ - starts[0];
761: for (j=0; j<sdim-1; j++) {
762: if ((*dxn++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
763: else tmp = tmp*dims[j] + dxn[-1] - starts[j+1];
764: }
765: dxn++;
766: jdxn[i] = tmp;
767: }
768: MatSetValuesBlockedLocal(mat,m,jdxm,n,jdxn,v,addv);
769: return(0);
770: }
774: /*@
775: MatSetStencil - Sets the grid information for setting values into a matrix via
776: MatSetValuesStencil()
778: Not Collective
780: Input Parameters:
781: + mat - the matrix
782: . dim - dimension of the grid 1, 2, or 3
783: . dims - number of grid points in x, y, and z direction, including ghost points on your processor
784: . starts - starting point of ghost nodes on your processor in x, y, and z direction
785: - dof - number of degrees of freedom per node
788: Inspired by the structured grid interface to the HYPRE package
789: (www.llnl.gov/CASC/hyper)
791: For matrices generated with DAGetMatrix() this routine is automatically called and so not needed by the
792: user.
793:
794: Level: beginner
796: Concepts: matrices^putting entries in
798: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal()
799: MatSetValues(), MatSetValuesBlockedStencil(), MatSetValuesStencil()
800: @*/
801: PetscErrorCode MatSetStencil(Mat mat,PetscInt dim,const PetscInt dims[],const PetscInt starts[],PetscInt dof)
802: {
803: PetscInt i;
810: mat->stencil.dim = dim + (dof > 1);
811: for (i=0; i<dim; i++) {
812: mat->stencil.dims[i] = dims[dim-i-1]; /* copy the values in backwards */
813: mat->stencil.starts[i] = starts[dim-i-1];
814: }
815: mat->stencil.dims[dim] = dof;
816: mat->stencil.starts[dim] = 0;
817: mat->stencil.noc = (PetscTruth)(dof == 1);
818: return(0);
819: }
823: /*@
824: MatSetValuesBlocked - Inserts or adds a block of values into a matrix.
826: Not Collective
828: Input Parameters:
829: + mat - the matrix
830: . v - a logically two-dimensional array of values
831: . m, idxm - the number of block rows and their global block indices
832: . n, idxn - the number of block columns and their global block indices
833: - addv - either ADD_VALUES or INSERT_VALUES, where
834: ADD_VALUES adds values to any existing entries, and
835: INSERT_VALUES replaces existing entries with new values
837: Notes:
838: By default the values, v, are row-oriented and unsorted. So the layout of
839: v is the same as for MatSetValues(). See MatSetOption() for other options.
841: Calls to MatSetValuesBlocked() with the INSERT_VALUES and ADD_VALUES
842: options cannot be mixed without intervening calls to the assembly
843: routines.
845: MatSetValuesBlocked() uses 0-based row and column numbers in Fortran
846: as well as in C.
848: Negative indices may be passed in idxm and idxn, these rows and columns are
849: simply ignored. This allows easily inserting element stiffness matrices
850: with homogeneous Dirchlet boundary conditions that you don't want represented
851: in the matrix.
853: Each time an entry is set within a sparse matrix via MatSetValues(),
854: internal searching must be done to determine where to place the the
855: data in the matrix storage space. By instead inserting blocks of
856: entries via MatSetValuesBlocked(), the overhead of matrix assembly is
857: reduced.
859: Restrictions:
860: MatSetValuesBlocked() is currently supported only for the BAIJ and SBAIJ formats
862: Level: intermediate
864: Concepts: matrices^putting entries in blocked
866: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesBlockedLocal()
867: @*/
868: PetscErrorCode MatSetValuesBlocked(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],const PetscScalar v[],InsertMode addv)
869: {
873: if (!m || !n) return(0); /* no values to insert */
876: MatPreallocated(mat);
880: if (mat->insertmode == NOT_SET_VALUES) {
881: mat->insertmode = addv;
882: }
883: #if defined(PETSC_USE_BOPT_g)
884: else if (mat->insertmode != addv) {
885: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
886: }
887: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
888: #endif
890: if (mat->assembled) {
891: mat->was_assembled = PETSC_TRUE;
892: mat->assembled = PETSC_FALSE;
893: }
894: PetscLogEventBegin(MAT_SetValues,mat,0,0,0);
895: if (!mat->ops->setvaluesblocked) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
896: (*mat->ops->setvaluesblocked)(mat,m,idxm,n,idxn,v,addv);
897: PetscLogEventEnd(MAT_SetValues,mat,0,0,0);
898: return(0);
899: }
903: /*@
904: MatGetValues - Gets a block of values from a matrix.
906: Not Collective; currently only returns a local block
908: Input Parameters:
909: + mat - the matrix
910: . v - a logically two-dimensional array for storing the values
911: . m, idxm - the number of rows and their global indices
912: - n, idxn - the number of columns and their global indices
914: Notes:
915: The user must allocate space (m*n PetscScalars) for the values, v.
916: The values, v, are then returned in a row-oriented format,
917: analogous to that used by default in MatSetValues().
919: MatGetValues() uses 0-based row and column numbers in
920: Fortran as well as in C.
922: MatGetValues() requires that the matrix has been assembled
923: with MatAssemblyBegin()/MatAssemblyEnd(). Thus, calls to
924: MatSetValues() and MatGetValues() CANNOT be made in succession
925: without intermediate matrix assembly.
927: Level: advanced
929: Concepts: matrices^accessing values
931: .seealso: MatGetRow(), MatGetSubmatrices(), MatSetValues()
932: @*/
933: PetscErrorCode MatGetValues(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],PetscScalar v[])
934: {
940: MatPreallocated(mat);
944: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
945: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
946: if (!mat->ops->getvalues) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
948: PetscLogEventBegin(MAT_GetValues,mat,0,0,0);
949: (*mat->ops->getvalues)(mat,m,idxm,n,idxn,v);
950: PetscLogEventEnd(MAT_GetValues,mat,0,0,0);
951: return(0);
952: }
956: /*@
957: MatSetLocalToGlobalMapping - Sets a local-to-global numbering for use by
958: the routine MatSetValuesLocal() to allow users to insert matrix entries
959: using a local (per-processor) numbering.
961: Not Collective
963: Input Parameters:
964: + x - the matrix
965: - mapping - mapping created with ISLocalToGlobalMappingCreate()
966: or ISLocalToGlobalMappingCreateIS()
968: Level: intermediate
970: Concepts: matrices^local to global mapping
971: Concepts: local to global mapping^for matrices
973: .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesLocal()
974: @*/
975: PetscErrorCode MatSetLocalToGlobalMapping(Mat x,ISLocalToGlobalMapping mapping)
976: {
981: MatPreallocated(x);
983: if (x->mapping) {
984: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Mapping already set for matrix");
985: }
987: if (x->ops->setlocaltoglobalmapping) {
988: (*x->ops->setlocaltoglobalmapping)(x,mapping);
989: } else {
990: x->mapping = mapping;
991: PetscObjectReference((PetscObject)mapping);
992: }
993: return(0);
994: }
998: /*@
999: MatSetLocalToGlobalMappingBlock - Sets a local-to-global numbering for use
1000: by the routine MatSetValuesBlockedLocal() to allow users to insert matrix
1001: entries using a local (per-processor) numbering.
1003: Not Collective
1005: Input Parameters:
1006: + x - the matrix
1007: - mapping - mapping created with ISLocalToGlobalMappingCreate() or
1008: ISLocalToGlobalMappingCreateIS()
1010: Level: intermediate
1012: Concepts: matrices^local to global mapping blocked
1013: Concepts: local to global mapping^for matrices, blocked
1015: .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesBlockedLocal(),
1016: MatSetValuesBlocked(), MatSetValuesLocal()
1017: @*/
1018: PetscErrorCode MatSetLocalToGlobalMappingBlock(Mat x,ISLocalToGlobalMapping mapping)
1019: {
1024: MatPreallocated(x);
1026: if (x->bmapping) {
1027: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Mapping already set for matrix");
1028: }
1029:
1030: x->bmapping = mapping;
1031: PetscObjectReference((PetscObject)mapping);
1032: return(0);
1033: }
1037: /*@
1038: MatSetValuesLocal - Inserts or adds values into certain locations of a matrix,
1039: using a local ordering of the nodes.
1041: Not Collective
1043: Input Parameters:
1044: + x - the matrix
1045: . nrow, irow - number of rows and their local indices
1046: . ncol, icol - number of columns and their local indices
1047: . y - a logically two-dimensional array of values
1048: - addv - either INSERT_VALUES or ADD_VALUES, where
1049: ADD_VALUES adds values to any existing entries, and
1050: INSERT_VALUES replaces existing entries with new values
1052: Notes:
1053: Before calling MatSetValuesLocal(), the user must first set the
1054: local-to-global mapping by calling MatSetLocalToGlobalMapping().
1056: Calls to MatSetValuesLocal() with the INSERT_VALUES and ADD_VALUES
1057: options cannot be mixed without intervening calls to the assembly
1058: routines.
1060: These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
1061: MUST be called after all calls to MatSetValuesLocal() have been completed.
1063: Level: intermediate
1065: Concepts: matrices^putting entries in with local numbering
1067: .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetLocalToGlobalMapping(),
1068: MatSetValueLocal()
1069: @*/
1070: PetscErrorCode MatSetValuesLocal(Mat mat,PetscInt nrow,const PetscInt irow[],PetscInt ncol,const PetscInt icol[],const PetscScalar y[],InsertMode addv)
1071: {
1073: PetscInt irowm[2048],icolm[2048];
1078: MatPreallocated(mat);
1083: if (mat->insertmode == NOT_SET_VALUES) {
1084: mat->insertmode = addv;
1085: }
1086: #if defined(PETSC_USE_BOPT_g)
1087: else if (mat->insertmode != addv) {
1088: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
1089: }
1090: if (!mat->ops->setvalueslocal && (nrow > 2048 || ncol > 2048)) {
1091: SETERRQ2(PETSC_ERR_SUP,"Number column/row indices must be <= 2048: are %D %D",nrow,ncol);
1092: }
1093: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1094: #endif
1096: if (mat->assembled) {
1097: mat->was_assembled = PETSC_TRUE;
1098: mat->assembled = PETSC_FALSE;
1099: }
1100: PetscLogEventBegin(MAT_SetValues,mat,0,0,0);
1101: if (!mat->ops->setvalueslocal) {
1102: ISLocalToGlobalMappingApply(mat->mapping,nrow,irow,irowm);
1103: ISLocalToGlobalMappingApply(mat->mapping,ncol,icol,icolm);
1104: (*mat->ops->setvalues)(mat,nrow,irowm,ncol,icolm,y,addv);
1105: } else {
1106: (*mat->ops->setvalueslocal)(mat,nrow,irow,ncol,icol,y,addv);
1107: }
1108: PetscLogEventEnd(MAT_SetValues,mat,0,0,0);
1109: return(0);
1110: }
1114: /*@
1115: MatSetValuesBlockedLocal - Inserts or adds values into certain locations of a matrix,
1116: using a local ordering of the nodes a block at a time.
1118: Not Collective
1120: Input Parameters:
1121: + x - the matrix
1122: . nrow, irow - number of rows and their local indices
1123: . ncol, icol - number of columns and their local indices
1124: . y - a logically two-dimensional array of values
1125: - addv - either INSERT_VALUES or ADD_VALUES, where
1126: ADD_VALUES adds values to any existing entries, and
1127: INSERT_VALUES replaces existing entries with new values
1129: Notes:
1130: Before calling MatSetValuesBlockedLocal(), the user must first set the
1131: local-to-global mapping by calling MatSetLocalToGlobalMappingBlock(),
1132: where the mapping MUST be set for matrix blocks, not for matrix elements.
1134: Calls to MatSetValuesBlockedLocal() with the INSERT_VALUES and ADD_VALUES
1135: options cannot be mixed without intervening calls to the assembly
1136: routines.
1138: These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
1139: MUST be called after all calls to MatSetValuesBlockedLocal() have been completed.
1141: Level: intermediate
1143: Concepts: matrices^putting blocked values in with local numbering
1145: .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesLocal(), MatSetLocalToGlobalMappingBlock(), MatSetValuesBlocked()
1146: @*/
1147: PetscErrorCode MatSetValuesBlockedLocal(Mat mat,PetscInt nrow,const PetscInt irow[],PetscInt ncol,const PetscInt icol[],const PetscScalar y[],InsertMode addv)
1148: {
1150: PetscInt irowm[2048],icolm[2048];
1155: MatPreallocated(mat);
1159: if (mat->insertmode == NOT_SET_VALUES) {
1160: mat->insertmode = addv;
1161: }
1162: #if defined(PETSC_USE_BOPT_g)
1163: else if (mat->insertmode != addv) {
1164: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
1165: }
1166: if (!mat->bmapping) {
1167: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Local to global never set with MatSetLocalToGlobalMappingBlock()");
1168: }
1169: if (nrow > 2048 || ncol > 2048) {
1170: SETERRQ2(PETSC_ERR_SUP,"Number column/row indices must be <= 2048: are %D %D",nrow,ncol);
1171: }
1172: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1173: #endif
1175: if (mat->assembled) {
1176: mat->was_assembled = PETSC_TRUE;
1177: mat->assembled = PETSC_FALSE;
1178: }
1179: PetscLogEventBegin(MAT_SetValues,mat,0,0,0);
1180: ISLocalToGlobalMappingApply(mat->bmapping,nrow,irow,irowm);
1181: ISLocalToGlobalMappingApply(mat->bmapping,ncol,icol,icolm);
1182: (*mat->ops->setvaluesblocked)(mat,nrow,irowm,ncol,icolm,y,addv);
1183: PetscLogEventEnd(MAT_SetValues,mat,0,0,0);
1184: return(0);
1185: }
1187: /* --------------------------------------------------------*/
1190: /*@
1191: MatMult - Computes the matrix-vector product, y = Ax.
1193: Collective on Mat and Vec
1195: Input Parameters:
1196: + mat - the matrix
1197: - x - the vector to be multiplied
1199: Output Parameters:
1200: . y - the result
1202: Notes:
1203: The vectors x and y cannot be the same. I.e., one cannot
1204: call MatMult(A,y,y).
1206: Level: beginner
1208: Concepts: matrix-vector product
1210: .seealso: MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd()
1211: @*/
1212: PetscErrorCode MatMult(Mat mat,Vec x,Vec y)
1213: {
1219: MatPreallocated(mat);
1223: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1224: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1225: if (x == y) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1226: #ifndef PETSC_HAVE_CONSTRAINTS
1227: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
1228: if (mat->M != y->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->M,y->N);
1229: if (mat->m != y->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: local dim %D %D",mat->m,y->n);
1230: #endif
1232: if (mat->nullsp) {
1233: MatNullSpaceRemove(mat->nullsp,x,&x);
1234: }
1236: PetscLogEventBegin(MAT_Mult,mat,x,y,0);
1237: (*mat->ops->mult)(mat,x,y);
1238: PetscLogEventEnd(MAT_Mult,mat,x,y,0);
1240: if (mat->nullsp) {
1241: MatNullSpaceRemove(mat->nullsp,y,PETSC_NULL);
1242: }
1243: PetscObjectIncreaseState((PetscObject)y);
1244: return(0);
1245: }
1249: /*@
1250: MatMultTranspose - Computes matrix transpose times a vector.
1252: Collective on Mat and Vec
1254: Input Parameters:
1255: + mat - the matrix
1256: - x - the vector to be multilplied
1258: Output Parameters:
1259: . y - the result
1261: Notes:
1262: The vectors x and y cannot be the same. I.e., one cannot
1263: call MatMultTranspose(A,y,y).
1265: Level: beginner
1267: Concepts: matrix vector product^transpose
1269: .seealso: MatMult(), MatMultAdd(), MatMultTransposeAdd()
1270: @*/
1271: PetscErrorCode MatMultTranspose(Mat mat,Vec x,Vec y)
1272: {
1274: PetscTruth flg1, flg2;
1279: MatPreallocated(mat);
1283: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1284: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1285: if (x == y) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1286: #ifndef PETSC_HAVE_CONSTRAINTS
1287: if (mat->M != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->M,x->N);
1288: if (mat->N != y->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->N,y->N);
1289: #endif
1291: if (!mat->ops->multtranspose) SETERRQ(PETSC_ERR_SUP, "Operation not supported");
1292: PetscLogEventBegin(MAT_MultTranspose,mat,x,y,0);
1293: if (!mat->ops->multtranspose) SETERRQ(PETSC_ERR_SUP,"This matrix type does not have a multiply tranpose defined");
1294:
1295: PetscTypeCompare((PetscObject)mat,MATSEQSBAIJ,&flg1);
1296: PetscTypeCompare((PetscObject)mat,MATMPISBAIJ,&flg2);
1297: if (flg1 || flg2) { /* mat is in sbaij format */
1298: (*mat->ops->mult)(mat,x,y);
1299: } else {
1300: (*mat->ops->multtranspose)(mat,x,y);
1301: }
1302: PetscLogEventEnd(MAT_MultTranspose,mat,x,y,0);
1303: PetscObjectIncreaseState((PetscObject)y);
1304: return(0);
1305: }
1309: /*@
1310: MatMultAdd - Computes v3 = v2 + A * v1.
1312: Collective on Mat and Vec
1314: Input Parameters:
1315: + mat - the matrix
1316: - v1, v2 - the vectors
1318: Output Parameters:
1319: . v3 - the result
1321: Notes:
1322: The vectors v1 and v3 cannot be the same. I.e., one cannot
1323: call MatMultAdd(A,v1,v2,v1).
1325: Level: beginner
1327: Concepts: matrix vector product^addition
1329: .seealso: MatMultTranspose(), MatMult(), MatMultTransposeAdd()
1330: @*/
1331: PetscErrorCode MatMultAdd(Mat mat,Vec v1,Vec v2,Vec v3)
1332: {
1338: MatPreallocated(mat);
1343: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1344: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1345: if (mat->N != v1->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->N,v1->N);
1346: if (mat->M != v2->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->M,v2->N);
1347: if (mat->M != v3->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->M,v3->N);
1348: if (mat->m != v3->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: local dim %D %D",mat->m,v3->n);
1349: if (mat->m != v2->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: local dim %D %D",mat->m,v2->n);
1350: if (v1 == v3) SETERRQ(PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors");
1352: PetscLogEventBegin(MAT_MultAdd,mat,v1,v2,v3);
1353: (*mat->ops->multadd)(mat,v1,v2,v3);
1354: PetscLogEventEnd(MAT_MultAdd,mat,v1,v2,v3);
1355: PetscObjectIncreaseState((PetscObject)v3);
1356: return(0);
1357: }
1361: /*@
1362: MatMultTransposeAdd - Computes v3 = v2 + A' * v1.
1364: Collective on Mat and Vec
1366: Input Parameters:
1367: + mat - the matrix
1368: - v1, v2 - the vectors
1370: Output Parameters:
1371: . v3 - the result
1373: Notes:
1374: The vectors v1 and v3 cannot be the same. I.e., one cannot
1375: call MatMultTransposeAdd(A,v1,v2,v1).
1377: Level: beginner
1379: Concepts: matrix vector product^transpose and addition
1381: .seealso: MatMultTranspose(), MatMultAdd(), MatMult()
1382: @*/
1383: PetscErrorCode MatMultTransposeAdd(Mat mat,Vec v1,Vec v2,Vec v3)
1384: {
1390: MatPreallocated(mat);
1395: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1396: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1397: if (!mat->ops->multtransposeadd) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1398: if (v1 == v3) SETERRQ(PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors");
1399: if (mat->M != v1->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->M,v1->N);
1400: if (mat->N != v2->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->N,v2->N);
1401: if (mat->N != v3->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->N,v3->N);
1403: PetscLogEventBegin(MAT_MultTransposeAdd,mat,v1,v2,v3);
1404: (*mat->ops->multtransposeadd)(mat,v1,v2,v3);
1405: PetscLogEventEnd(MAT_MultTransposeAdd,mat,v1,v2,v3);
1406: PetscObjectIncreaseState((PetscObject)v3);
1407: return(0);
1408: }
1412: /*@
1413: MatMultConstrained - The inner multiplication routine for a
1414: constrained matrix P^T A P.
1416: Collective on Mat and Vec
1418: Input Parameters:
1419: + mat - the matrix
1420: - x - the vector to be multilplied
1422: Output Parameters:
1423: . y - the result
1425: Notes:
1426: The vectors x and y cannot be the same. I.e., one cannot
1427: call MatMult(A,y,y).
1429: Level: beginner
1431: .keywords: matrix, multiply, matrix-vector product, constraint
1432: .seealso: MatMult(), MatMultTrans(), MatMultAdd(), MatMultTransAdd()
1433: @*/
1434: PetscErrorCode MatMultConstrained(Mat mat,Vec x,Vec y)
1435: {
1442: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1443: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1444: if (x == y) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1445: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
1446: if (mat->M != y->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->M,y->N);
1447: if (mat->m != y->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: local dim %D %D",mat->m,y->n);
1449: PetscLogEventBegin(MAT_MultConstrained,mat,x,y,0);
1450: (*mat->ops->multconstrained)(mat,x,y);
1451: PetscLogEventEnd(MAT_MultConstrained,mat,x,y,0);
1452: PetscObjectIncreaseState((PetscObject)y);
1454: return(0);
1455: }
1459: /*@
1460: MatMultTransposeConstrained - The inner multiplication routine for a
1461: constrained matrix P^T A^T P.
1463: Collective on Mat and Vec
1465: Input Parameters:
1466: + mat - the matrix
1467: - x - the vector to be multilplied
1469: Output Parameters:
1470: . y - the result
1472: Notes:
1473: The vectors x and y cannot be the same. I.e., one cannot
1474: call MatMult(A,y,y).
1476: Level: beginner
1478: .keywords: matrix, multiply, matrix-vector product, constraint
1479: .seealso: MatMult(), MatMultTrans(), MatMultAdd(), MatMultTransAdd()
1480: @*/
1481: PetscErrorCode MatMultTransposeConstrained(Mat mat,Vec x,Vec y)
1482: {
1489: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1490: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1491: if (x == y) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1492: if (mat->M != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
1493: if (mat->N != y->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->M,y->N);
1495: PetscLogEventBegin(MAT_MultConstrained,mat,x,y,0);
1496: (*mat->ops->multtransposeconstrained)(mat,x,y);
1497: PetscLogEventEnd(MAT_MultConstrained,mat,x,y,0);
1498: PetscObjectIncreaseState((PetscObject)y);
1500: return(0);
1501: }
1502: /* ------------------------------------------------------------*/
1505: /*@C
1506: MatGetInfo - Returns information about matrix storage (number of
1507: nonzeros, memory, etc.).
1509: Collective on Mat if MAT_GLOBAL_MAX or MAT_GLOBAL_SUM is used
1510: as the flag
1512: Input Parameters:
1513: . mat - the matrix
1515: Output Parameters:
1516: + flag - flag indicating the type of parameters to be returned
1517: (MAT_LOCAL - local matrix, MAT_GLOBAL_MAX - maximum over all processors,
1518: MAT_GLOBAL_SUM - sum over all processors)
1519: - info - matrix information context
1521: Notes:
1522: The MatInfo context contains a variety of matrix data, including
1523: number of nonzeros allocated and used, number of mallocs during
1524: matrix assembly, etc. Additional information for factored matrices
1525: is provided (such as the fill ratio, number of mallocs during
1526: factorization, etc.). Much of this info is printed to STDOUT
1527: when using the runtime options
1528: $ -log_info -mat_view_info
1530: Example for C/C++ Users:
1531: See the file ${PETSC_DIR}/include/petscmat.h for a complete list of
1532: data within the MatInfo context. For example,
1533: .vb
1534: MatInfo info;
1535: Mat A;
1536: double mal, nz_a, nz_u;
1538: MatGetInfo(A,MAT_LOCAL,&info);
1539: mal = info.mallocs;
1540: nz_a = info.nz_allocated;
1541: .ve
1543: Example for Fortran Users:
1544: Fortran users should declare info as a double precision
1545: array of dimension MAT_INFO_SIZE, and then extract the parameters
1546: of interest. See the file ${PETSC_DIR}/include/finclude/petscmat.h
1547: a complete list of parameter names.
1548: .vb
1549: double precision info(MAT_INFO_SIZE)
1550: double precision mal, nz_a
1551: Mat A
1552: integer ierr
1554: call MatGetInfo(A,MAT_LOCAL,info,ierr)
1555: mal = info(MAT_INFO_MALLOCS)
1556: nz_a = info(MAT_INFO_NZ_ALLOCATED)
1557: .ve
1559: Level: intermediate
1561: Concepts: matrices^getting information on
1562:
1563: @*/
1564: PetscErrorCode MatGetInfo(Mat mat,MatInfoType flag,MatInfo *info)
1565: {
1571: MatPreallocated(mat);
1573: if (!mat->ops->getinfo) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1574: (*mat->ops->getinfo)(mat,flag,info);
1575: return(0);
1576: }
1578: /* ----------------------------------------------------------*/
1581: /*@C
1582: MatILUDTFactor - Performs a drop tolerance ILU factorization.
1584: Collective on Mat
1586: Input Parameters:
1587: + mat - the matrix
1588: . info - information about the factorization to be done
1589: . row - row permutation
1590: - col - column permutation
1592: Output Parameters:
1593: . fact - the factored matrix
1595: Level: developer
1597: Notes:
1598: Most users should employ the simplified KSP interface for linear solvers
1599: instead of working directly with matrix algebra routines such as this.
1600: See, e.g., KSPCreate().
1602: This is currently only supported for the SeqAIJ matrix format using code
1603: from Yousef Saad's SPARSEKIT2 package (translated to C with f2c) and/or
1604: Matlab. SPARSEKIT2 is copyrighted by Yousef Saad with the GNU copyright
1605: and thus can be distributed with PETSc.
1607: Concepts: matrices^ILUDT factorization
1609: .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
1610: @*/
1611: PetscErrorCode MatILUDTFactor(Mat mat,MatFactorInfo *info,IS row,IS col,Mat *fact)
1612: {
1618: MatPreallocated(mat);
1623: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1624: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1625: if (!mat->ops->iludtfactor) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1627: PetscLogEventBegin(MAT_ILUFactor,mat,row,col,0);
1628: (*mat->ops->iludtfactor)(mat,info,row,col,fact);
1629: PetscLogEventEnd(MAT_ILUFactor,mat,row,col,0);
1630: PetscObjectIncreaseState((PetscObject)*fact);
1632: return(0);
1633: }
1637: /*@
1638: MatLUFactor - Performs in-place LU factorization of matrix.
1640: Collective on Mat
1642: Input Parameters:
1643: + mat - the matrix
1644: . row - row permutation
1645: . col - column permutation
1646: - info - options for factorization, includes
1647: $ fill - expected fill as ratio of original fill.
1648: $ dtcol - pivot tolerance (0 no pivot, 1 full column pivoting)
1649: $ Run with the option -log_info to determine an optimal value to use
1651: Notes:
1652: Most users should employ the simplified KSP interface for linear solvers
1653: instead of working directly with matrix algebra routines such as this.
1654: See, e.g., KSPCreate().
1656: This changes the state of the matrix to a factored matrix; it cannot be used
1657: for example with MatSetValues() unless one first calls MatSetUnfactored().
1659: Level: developer
1661: Concepts: matrices^LU factorization
1663: .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(),
1664: MatGetOrdering(), MatSetUnfactored(), MatFactorInfo
1666: @*/
1667: PetscErrorCode MatLUFactor(Mat mat,IS row,IS col,MatFactorInfo *info)
1668: {
1677: MatPreallocated(mat);
1678: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1679: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1680: if (!mat->ops->lufactor) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1682: PetscLogEventBegin(MAT_LUFactor,mat,row,col,0);
1683: (*mat->ops->lufactor)(mat,row,col,info);
1684: PetscLogEventEnd(MAT_LUFactor,mat,row,col,0);
1685: PetscObjectIncreaseState((PetscObject)mat);
1686: return(0);
1687: }
1691: /*@
1692: MatILUFactor - Performs in-place ILU factorization of matrix.
1694: Collective on Mat
1696: Input Parameters:
1697: + mat - the matrix
1698: . row - row permutation
1699: . col - column permutation
1700: - info - structure containing
1701: $ levels - number of levels of fill.
1702: $ expected fill - as ratio of original fill.
1703: $ 1 or 0 - indicating force fill on diagonal (improves robustness for matrices
1704: missing diagonal entries)
1706: Notes:
1707: Probably really in-place only when level of fill is zero, otherwise allocates
1708: new space to store factored matrix and deletes previous memory.
1710: Most users should employ the simplified KSP interface for linear solvers
1711: instead of working directly with matrix algebra routines such as this.
1712: See, e.g., KSPCreate().
1714: Level: developer
1716: Concepts: matrices^ILU factorization
1718: .seealso: MatILUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
1719: @*/
1720: PetscErrorCode MatILUFactor(Mat mat,IS row,IS col,MatFactorInfo *info)
1721: {
1730: MatPreallocated(mat);
1731: if (mat->M != mat->N) SETERRQ(PETSC_ERR_ARG_WRONG,"matrix must be square");
1732: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1733: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1734: if (!mat->ops->ilufactor) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1736: PetscLogEventBegin(MAT_ILUFactor,mat,row,col,0);
1737: (*mat->ops->ilufactor)(mat,row,col,info);
1738: PetscLogEventEnd(MAT_ILUFactor,mat,row,col,0);
1739: PetscObjectIncreaseState((PetscObject)mat);
1740: return(0);
1741: }
1745: /*@
1746: MatLUFactorSymbolic - Performs symbolic LU factorization of matrix.
1747: Call this routine before calling MatLUFactorNumeric().
1749: Collective on Mat
1751: Input Parameters:
1752: + mat - the matrix
1753: . row, col - row and column permutations
1754: - info - options for factorization, includes
1755: $ fill - expected fill as ratio of original fill.
1756: $ dtcol - pivot tolerance (0 no pivot, 1 full column pivoting)
1757: $ Run with the option -log_info to determine an optimal value to use
1759: Output Parameter:
1760: . fact - new matrix that has been symbolically factored
1762: Notes:
1763: See the users manual for additional information about
1764: choosing the fill factor for better efficiency.
1766: Most users should employ the simplified KSP interface for linear solvers
1767: instead of working directly with matrix algebra routines such as this.
1768: See, e.g., KSPCreate().
1770: Level: developer
1772: Concepts: matrices^LU symbolic factorization
1774: .seealso: MatLUFactor(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
1775: @*/
1776: PetscErrorCode MatLUFactorSymbolic(Mat mat,IS row,IS col,MatFactorInfo *info,Mat *fact)
1777: {
1786: MatPreallocated(mat);
1788: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1789: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1790: if (!mat->ops->lufactorsymbolic) SETERRQ1(PETSC_ERR_SUP,"Matrix type %s symbolic LU",mat->type_name);
1792: PetscLogEventBegin(MAT_LUFactorSymbolic,mat,row,col,0);
1793: (*mat->ops->lufactorsymbolic)(mat,row,col,info,fact);
1794: PetscLogEventEnd(MAT_LUFactorSymbolic,mat,row,col,0);
1795: PetscObjectIncreaseState((PetscObject)*fact);
1796: return(0);
1797: }
1801: /*@
1802: MatLUFactorNumeric - Performs numeric LU factorization of a matrix.
1803: Call this routine after first calling MatLUFactorSymbolic().
1805: Collective on Mat
1807: Input Parameters:
1808: + mat - the matrix
1809: - fact - the matrix generated for the factor, from MatLUFactorSymbolic()
1811: Notes:
1812: See MatLUFactor() for in-place factorization. See
1813: MatCholeskyFactorNumeric() for the symmetric, positive definite case.
1815: Most users should employ the simplified KSP interface for linear solvers
1816: instead of working directly with matrix algebra routines such as this.
1817: See, e.g., KSPCreate().
1819: Level: developer
1821: Concepts: matrices^LU numeric factorization
1823: .seealso: MatLUFactorSymbolic(), MatLUFactor(), MatCholeskyFactor()
1824: @*/
1825: PetscErrorCode MatLUFactorNumeric(Mat mat,Mat *fact)
1826: {
1832: MatPreallocated(mat);
1835: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1836: if (mat->M != (*fact)->M || mat->N != (*fact)->N) {
1837: SETERRQ4(PETSC_ERR_ARG_SIZ,"Mat mat,Mat *fact: global dimensions are different %D should = %D %D should = %D",
1838: mat->M,(*fact)->M,mat->N,(*fact)->N);
1839: }
1840: if (!(*fact)->ops->lufactornumeric) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1842: PetscLogEventBegin(MAT_LUFactorNumeric,mat,*fact,0,0);
1843: (*(*fact)->ops->lufactornumeric)(mat,fact);
1844: PetscLogEventEnd(MAT_LUFactorNumeric,mat,*fact,0,0);
1846: MatView_Private(*fact);
1847: PetscObjectIncreaseState((PetscObject)*fact);
1848: return(0);
1849: }
1853: /*@
1854: MatCholeskyFactor - Performs in-place Cholesky factorization of a
1855: symmetric matrix.
1857: Collective on Mat
1859: Input Parameters:
1860: + mat - the matrix
1861: . perm - row and column permutations
1862: - f - expected fill as ratio of original fill
1864: Notes:
1865: See MatLUFactor() for the nonsymmetric case. See also
1866: MatCholeskyFactorSymbolic(), and MatCholeskyFactorNumeric().
1868: Most users should employ the simplified KSP interface for linear solvers
1869: instead of working directly with matrix algebra routines such as this.
1870: See, e.g., KSPCreate().
1872: Level: developer
1874: Concepts: matrices^Cholesky factorization
1876: .seealso: MatLUFactor(), MatCholeskyFactorSymbolic(), MatCholeskyFactorNumeric()
1877: MatGetOrdering()
1879: @*/
1880: PetscErrorCode MatCholeskyFactor(Mat mat,IS perm,MatFactorInfo *info)
1881: {
1887: MatPreallocated(mat);
1890: if (mat->M != mat->N) SETERRQ(PETSC_ERR_ARG_WRONG,"Matrix must be square");
1891: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1892: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1893: if (!mat->ops->choleskyfactor) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1895: PetscLogEventBegin(MAT_CholeskyFactor,mat,perm,0,0);
1896: (*mat->ops->choleskyfactor)(mat,perm,info);
1897: PetscLogEventEnd(MAT_CholeskyFactor,mat,perm,0,0);
1898: PetscObjectIncreaseState((PetscObject)mat);
1899: return(0);
1900: }
1904: /*@
1905: MatCholeskyFactorSymbolic - Performs symbolic Cholesky factorization
1906: of a symmetric matrix.
1908: Collective on Mat
1910: Input Parameters:
1911: + mat - the matrix
1912: . perm - row and column permutations
1913: - info - options for factorization, includes
1914: $ fill - expected fill as ratio of original fill.
1915: $ dtcol - pivot tolerance (0 no pivot, 1 full column pivoting)
1916: $ Run with the option -log_info to determine an optimal value to use
1918: Output Parameter:
1919: . fact - the factored matrix
1921: Notes:
1922: See MatLUFactorSymbolic() for the nonsymmetric case. See also
1923: MatCholeskyFactor() and MatCholeskyFactorNumeric().
1925: Most users should employ the simplified KSP interface for linear solvers
1926: instead of working directly with matrix algebra routines such as this.
1927: See, e.g., KSPCreate().
1929: Level: developer
1931: Concepts: matrices^Cholesky symbolic factorization
1933: .seealso: MatLUFactorSymbolic(), MatCholeskyFactor(), MatCholeskyFactorNumeric()
1934: MatGetOrdering()
1936: @*/
1937: PetscErrorCode MatCholeskyFactorSymbolic(Mat mat,IS perm,MatFactorInfo *info,Mat *fact)
1938: {
1944: MatPreallocated(mat);
1948: if (mat->M != mat->N) SETERRQ(PETSC_ERR_ARG_WRONG,"Matrix must be square");
1949: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1950: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1951: if (!mat->ops->choleskyfactorsymbolic) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1953: PetscLogEventBegin(MAT_CholeskyFactorSymbolic,mat,perm,0,0);
1954: (*mat->ops->choleskyfactorsymbolic)(mat,perm,info,fact);
1955: PetscLogEventEnd(MAT_CholeskyFactorSymbolic,mat,perm,0,0);
1956: PetscObjectIncreaseState((PetscObject)*fact);
1957: return(0);
1958: }
1962: /*@
1963: MatCholeskyFactorNumeric - Performs numeric Cholesky factorization
1964: of a symmetric matrix. Call this routine after first calling
1965: MatCholeskyFactorSymbolic().
1967: Collective on Mat
1969: Input Parameter:
1970: . mat - the initial matrix
1972: Output Parameter:
1973: . fact - the factored matrix
1975: Notes:
1976: Most users should employ the simplified KSP interface for linear solvers
1977: instead of working directly with matrix algebra routines such as this.
1978: See, e.g., KSPCreate().
1980: Level: developer
1982: Concepts: matrices^Cholesky numeric factorization
1984: .seealso: MatCholeskyFactorSymbolic(), MatCholeskyFactor(), MatLUFactorNumeric()
1985: @*/
1986: PetscErrorCode MatCholeskyFactorNumeric(Mat mat,Mat *fact)
1987: {
1993: MatPreallocated(mat);
1995: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1996: if (!(*fact)->ops->choleskyfactornumeric) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
1997: if (mat->M != (*fact)->M || mat->N != (*fact)->N) {
1998: SETERRQ4(PETSC_ERR_ARG_SIZ,"Mat mat,Mat *fact: global dim %D should = %D %D should = %D",
1999: mat->M,(*fact)->M,mat->N,(*fact)->N);
2000: }
2002: PetscLogEventBegin(MAT_CholeskyFactorNumeric,mat,*fact,0,0);
2003: (*(*fact)->ops->choleskyfactornumeric)(mat,fact);
2004: PetscLogEventEnd(MAT_CholeskyFactorNumeric,mat,*fact,0,0);
2005: PetscObjectIncreaseState((PetscObject)*fact);
2006: return(0);
2007: }
2009: /* ----------------------------------------------------------------*/
2012: /*@
2013: MatSolve - Solves A x = b, given a factored matrix.
2015: Collective on Mat and Vec
2017: Input Parameters:
2018: + mat - the factored matrix
2019: - b - the right-hand-side vector
2021: Output Parameter:
2022: . x - the result vector
2024: Notes:
2025: The vectors b and x cannot be the same. I.e., one cannot
2026: call MatSolve(A,x,x).
2028: Notes:
2029: Most users should employ the simplified KSP interface for linear solvers
2030: instead of working directly with matrix algebra routines such as this.
2031: See, e.g., KSPCreate().
2033: Level: developer
2035: Concepts: matrices^triangular solves
2037: .seealso: MatSolveAdd(), MatSolveTranspose(), MatSolveTransposeAdd()
2038: @*/
2039: PetscErrorCode MatSolve(Mat mat,Vec b,Vec x)
2040: {
2046: MatPreallocated(mat);
2051: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2052: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2053: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
2054: if (mat->M != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->M,b->N);
2055: if (mat->m != b->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->m,b->n);
2056: if (!mat->M && !mat->N) return(0);
2058: if (!mat->ops->solve) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2059: PetscLogEventBegin(MAT_Solve,mat,b,x,0);
2060: (*mat->ops->solve)(mat,b,x);
2061: PetscLogEventEnd(MAT_Solve,mat,b,x,0);
2062: PetscObjectIncreaseState((PetscObject)x);
2063: return(0);
2064: }
2068: /* @
2069: MatForwardSolve - Solves L x = b, given a factored matrix, A = LU.
2071: Collective on Mat and Vec
2073: Input Parameters:
2074: + mat - the factored matrix
2075: - b - the right-hand-side vector
2077: Output Parameter:
2078: . x - the result vector
2080: Notes:
2081: MatSolve() should be used for most applications, as it performs
2082: a forward solve followed by a backward solve.
2084: The vectors b and x cannot be the same. I.e., one cannot
2085: call MatForwardSolve(A,x,x).
2087: Most users should employ the simplified KSP interface for linear solvers
2088: instead of working directly with matrix algebra routines such as this.
2089: See, e.g., KSPCreate().
2091: Level: developer
2093: Concepts: matrices^forward solves
2095: .seealso: MatSolve(), MatBackwardSolve()
2096: @ */
2097: PetscErrorCode MatForwardSolve(Mat mat,Vec b,Vec x)
2098: {
2104: MatPreallocated(mat);
2109: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2110: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2111: if (!mat->ops->forwardsolve) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2112: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
2113: if (mat->M != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->M,b->N);
2114: if (mat->m != b->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->m,b->n);
2116: PetscLogEventBegin(MAT_ForwardSolve,mat,b,x,0);
2117: (*mat->ops->forwardsolve)(mat,b,x);
2118: PetscLogEventEnd(MAT_ForwardSolve,mat,b,x,0);
2119: PetscObjectIncreaseState((PetscObject)x);
2120: return(0);
2121: }
2125: /* @
2126: MatBackwardSolve - Solves U x = b, given a factored matrix, A = LU.
2128: Collective on Mat and Vec
2130: Input Parameters:
2131: + mat - the factored matrix
2132: - b - the right-hand-side vector
2134: Output Parameter:
2135: . x - the result vector
2137: Notes:
2138: MatSolve() should be used for most applications, as it performs
2139: a forward solve followed by a backward solve.
2141: The vectors b and x cannot be the same. I.e., one cannot
2142: call MatBackwardSolve(A,x,x).
2144: Most users should employ the simplified KSP interface for linear solvers
2145: instead of working directly with matrix algebra routines such as this.
2146: See, e.g., KSPCreate().
2148: Level: developer
2150: Concepts: matrices^backward solves
2152: .seealso: MatSolve(), MatForwardSolve()
2153: @ */
2154: PetscErrorCode MatBackwardSolve(Mat mat,Vec b,Vec x)
2155: {
2161: MatPreallocated(mat);
2166: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2167: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2168: if (!mat->ops->backwardsolve) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2169: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
2170: if (mat->M != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->M,b->N);
2171: if (mat->m != b->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->m,b->n);
2173: PetscLogEventBegin(MAT_BackwardSolve,mat,b,x,0);
2174: (*mat->ops->backwardsolve)(mat,b,x);
2175: PetscLogEventEnd(MAT_BackwardSolve,mat,b,x,0);
2176: PetscObjectIncreaseState((PetscObject)x);
2177: return(0);
2178: }
2182: /*@
2183: MatSolveAdd - Computes x = y + inv(A)*b, given a factored matrix.
2185: Collective on Mat and Vec
2187: Input Parameters:
2188: + mat - the factored matrix
2189: . b - the right-hand-side vector
2190: - y - the vector to be added to
2192: Output Parameter:
2193: . x - the result vector
2195: Notes:
2196: The vectors b and x cannot be the same. I.e., one cannot
2197: call MatSolveAdd(A,x,y,x).
2199: Most users should employ the simplified KSP interface for linear solvers
2200: instead of working directly with matrix algebra routines such as this.
2201: See, e.g., KSPCreate().
2203: Level: developer
2205: Concepts: matrices^triangular solves
2207: .seealso: MatSolve(), MatSolveTranspose(), MatSolveTransposeAdd()
2208: @*/
2209: PetscErrorCode MatSolveAdd(Mat mat,Vec b,Vec y,Vec x)
2210: {
2211: PetscScalar one = 1.0;
2212: Vec tmp;
2218: MatPreallocated(mat);
2225: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2226: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2227: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
2228: if (mat->M != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->M,b->N);
2229: if (mat->M != y->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->M,y->N);
2230: if (mat->m != b->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->m,b->n);
2231: if (x->n != y->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Vec x,Vec y: local dim %D %D",x->n,y->n);
2233: PetscLogEventBegin(MAT_SolveAdd,mat,b,x,y);
2234: if (mat->ops->solveadd) {
2235: (*mat->ops->solveadd)(mat,b,y,x);
2236: } else {
2237: /* do the solve then the add manually */
2238: if (x != y) {
2239: MatSolve(mat,b,x);
2240: VecAXPY(&one,y,x);
2241: } else {
2242: VecDuplicate(x,&tmp);
2243: PetscLogObjectParent(mat,tmp);
2244: VecCopy(x,tmp);
2245: MatSolve(mat,b,x);
2246: VecAXPY(&one,tmp,x);
2247: VecDestroy(tmp);
2248: }
2249: }
2250: PetscLogEventEnd(MAT_SolveAdd,mat,b,x,y);
2251: PetscObjectIncreaseState((PetscObject)x);
2252: return(0);
2253: }
2257: /*@
2258: MatSolveTranspose - Solves A' x = b, given a factored matrix.
2260: Collective on Mat and Vec
2262: Input Parameters:
2263: + mat - the factored matrix
2264: - b - the right-hand-side vector
2266: Output Parameter:
2267: . x - the result vector
2269: Notes:
2270: The vectors b and x cannot be the same. I.e., one cannot
2271: call MatSolveTranspose(A,x,x).
2273: Most users should employ the simplified KSP interface for linear solvers
2274: instead of working directly with matrix algebra routines such as this.
2275: See, e.g., KSPCreate().
2277: Level: developer
2279: Concepts: matrices^triangular solves
2281: .seealso: MatSolve(), MatSolveAdd(), MatSolveTransposeAdd()
2282: @*/
2283: PetscErrorCode MatSolveTranspose(Mat mat,Vec b,Vec x)
2284: {
2290: MatPreallocated(mat);
2295: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2296: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2297: if (!mat->ops->solvetranspose) SETERRQ1(PETSC_ERR_SUP,"Matrix type %s",mat->type_name);
2298: if (mat->M != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->M,x->N);
2299: if (mat->N != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->N,b->N);
2301: PetscLogEventBegin(MAT_SolveTranspose,mat,b,x,0);
2302: (*mat->ops->solvetranspose)(mat,b,x);
2303: PetscLogEventEnd(MAT_SolveTranspose,mat,b,x,0);
2304: PetscObjectIncreaseState((PetscObject)x);
2305: return(0);
2306: }
2310: /*@
2311: MatSolveTransposeAdd - Computes x = y + inv(Transpose(A)) b, given a
2312: factored matrix.
2314: Collective on Mat and Vec
2316: Input Parameters:
2317: + mat - the factored matrix
2318: . b - the right-hand-side vector
2319: - y - the vector to be added to
2321: Output Parameter:
2322: . x - the result vector
2324: Notes:
2325: The vectors b and x cannot be the same. I.e., one cannot
2326: call MatSolveTransposeAdd(A,x,y,x).
2328: Most users should employ the simplified KSP interface for linear solvers
2329: instead of working directly with matrix algebra routines such as this.
2330: See, e.g., KSPCreate().
2332: Level: developer
2334: Concepts: matrices^triangular solves
2336: .seealso: MatSolve(), MatSolveAdd(), MatSolveTranspose()
2337: @*/
2338: PetscErrorCode MatSolveTransposeAdd(Mat mat,Vec b,Vec y,Vec x)
2339: {
2340: PetscScalar one = 1.0;
2342: Vec tmp;
2347: MatPreallocated(mat);
2354: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2355: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2356: if (mat->M != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->M,x->N);
2357: if (mat->N != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->N,b->N);
2358: if (mat->N != y->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->N,y->N);
2359: if (x->n != y->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Vec x,Vec y: local dim %D %D",x->n,y->n);
2361: PetscLogEventBegin(MAT_SolveTransposeAdd,mat,b,x,y);
2362: if (mat->ops->solvetransposeadd) {
2363: (*mat->ops->solvetransposeadd)(mat,b,y,x);
2364: } else {
2365: /* do the solve then the add manually */
2366: if (x != y) {
2367: MatSolveTranspose(mat,b,x);
2368: VecAXPY(&one,y,x);
2369: } else {
2370: VecDuplicate(x,&tmp);
2371: PetscLogObjectParent(mat,tmp);
2372: VecCopy(x,tmp);
2373: MatSolveTranspose(mat,b,x);
2374: VecAXPY(&one,tmp,x);
2375: VecDestroy(tmp);
2376: }
2377: }
2378: PetscLogEventEnd(MAT_SolveTransposeAdd,mat,b,x,y);
2379: PetscObjectIncreaseState((PetscObject)x);
2380: return(0);
2381: }
2382: /* ----------------------------------------------------------------*/
2386: /*@
2387: MatRelax - Computes relaxation (SOR, Gauss-Seidel) sweeps.
2389: Collective on Mat and Vec
2391: Input Parameters:
2392: + mat - the matrix
2393: . b - the right hand side
2394: . omega - the relaxation factor
2395: . flag - flag indicating the type of SOR (see below)
2396: . shift - diagonal shift
2397: - its - the number of iterations
2398: - lits - the number of local iterations
2400: Output Parameters:
2401: . x - the solution (can contain an initial guess)
2403: SOR Flags:
2404: . SOR_FORWARD_SWEEP - forward SOR
2405: . SOR_BACKWARD_SWEEP - backward SOR
2406: . SOR_SYMMETRIC_SWEEP - SSOR (symmetric SOR)
2407: . SOR_LOCAL_FORWARD_SWEEP - local forward SOR
2408: . SOR_LOCAL_BACKWARD_SWEEP - local forward SOR
2409: . SOR_LOCAL_SYMMETRIC_SWEEP - local SSOR
2410: . SOR_APPLY_UPPER, SOR_APPLY_LOWER - applies
2411: upper/lower triangular part of matrix to
2412: vector (with omega)
2413: . SOR_ZERO_INITIAL_GUESS - zero initial guess
2415: Notes:
2416: SOR_LOCAL_FORWARD_SWEEP, SOR_LOCAL_BACKWARD_SWEEP, and
2417: SOR_LOCAL_SYMMETRIC_SWEEP perform seperate independent smoothings
2418: on each processor.
2420: Application programmers will not generally use MatRelax() directly,
2421: but instead will employ the KSP/PC interface.
2423: Notes for Advanced Users:
2424: The flags are implemented as bitwise inclusive or operations.
2425: For example, use (SOR_ZERO_INITIAL_GUESS | SOR_SYMMETRIC_SWEEP)
2426: to specify a zero initial guess for SSOR.
2428: Most users should employ the simplified KSP interface for linear solvers
2429: instead of working directly with matrix algebra routines such as this.
2430: See, e.g., KSPCreate().
2432: See also, MatPBRelax(). This routine will automatically call the point block
2433: version if the point version is not available.
2435: Level: developer
2437: Concepts: matrices^relaxation
2438: Concepts: matrices^SOR
2439: Concepts: matrices^Gauss-Seidel
2441: @*/
2442: PetscErrorCode MatRelax(Mat mat,Vec b,PetscReal omega,MatSORType flag,PetscReal shift,PetscInt its,PetscInt lits,Vec x)
2443: {
2449: MatPreallocated(mat);
2454: if (!mat->ops->relax && !mat->ops->pbrelax) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2455: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2456: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2457: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
2458: if (mat->M != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->M,b->N);
2459: if (mat->m != b->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->m,b->n);
2461: PetscLogEventBegin(MAT_Relax,mat,b,x,0);
2462: if (mat->ops->relax) {
2463: ierr =(*mat->ops->relax)(mat,b,omega,flag,shift,its,lits,x);
2464: } else {
2465: ierr =(*mat->ops->pbrelax)(mat,b,omega,flag,shift,its,lits,x);
2466: }
2467: PetscLogEventEnd(MAT_Relax,mat,b,x,0);
2468: PetscObjectIncreaseState((PetscObject)x);
2469: return(0);
2470: }
2474: /*@
2475: MatPBRelax - Computes relaxation (SOR, Gauss-Seidel) sweeps.
2477: Collective on Mat and Vec
2479: See MatRelax() for usage
2481: For multi-component PDEs where the Jacobian is stored in a point block format
2482: (with the PETSc BAIJ matrix formats) the relaxation is done one point block at
2483: a time. That is, the small (for example, 4 by 4) blocks along the diagonal are solved
2484: simultaneously (that is a 4 by 4 linear solve is done) to update all the values at a point.
2486: Level: developer
2488: @*/
2489: PetscErrorCode MatPBRelax(Mat mat,Vec b,PetscReal omega,MatSORType flag,PetscReal shift,PetscInt its,PetscInt lits,Vec x)
2490: {
2496: MatPreallocated(mat);
2501: if (!mat->ops->pbrelax) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2502: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2503: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2504: if (mat->N != x->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->N,x->N);
2505: if (mat->M != b->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->M,b->N);
2506: if (mat->m != b->n) SETERRQ2(PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->m,b->n);
2508: PetscLogEventBegin(MAT_Relax,mat,b,x,0);
2509: ierr =(*mat->ops->pbrelax)(mat,b,omega,flag,shift,its,lits,x);
2510: PetscLogEventEnd(MAT_Relax,mat,b,x,0);
2511: PetscObjectIncreaseState((PetscObject)x);
2512: return(0);
2513: }
2517: /*
2518: Default matrix copy routine.
2519: */
2520: PetscErrorCode MatCopy_Basic(Mat A,Mat B,MatStructure str)
2521: {
2522: PetscErrorCode ierr;
2523: PetscInt i,rstart,rend,nz;
2524: const PetscInt *cwork;
2525: const PetscScalar *vwork;
2528: if (B->assembled) {
2529: MatZeroEntries(B);
2530: }
2531: MatGetOwnershipRange(A,&rstart,&rend);
2532: for (i=rstart; i<rend; i++) {
2533: MatGetRow(A,i,&nz,&cwork,&vwork);
2534: MatSetValues(B,1,&i,nz,cwork,vwork,INSERT_VALUES);
2535: MatRestoreRow(A,i,&nz,&cwork,&vwork);
2536: }
2537: MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);
2538: MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);
2539: PetscObjectIncreaseState((PetscObject)B);
2540: return(0);
2541: }
2545: /*@C
2546: MatCopy - Copys a matrix to another matrix.
2548: Collective on Mat
2550: Input Parameters:
2551: + A - the matrix
2552: - str - SAME_NONZERO_PATTERN or DIFFERENT_NONZERO_PATTERN
2554: Output Parameter:
2555: . B - where the copy is put
2557: Notes:
2558: If you use SAME_NONZERO_PATTERN then the two matrices had better have the
2559: same nonzero pattern or the routine will crash.
2561: MatCopy() copies the matrix entries of a matrix to another existing
2562: matrix (after first zeroing the second matrix). A related routine is
2563: MatConvert(), which first creates a new matrix and then copies the data.
2565: Level: intermediate
2566:
2567: Concepts: matrices^copying
2569: .seealso: MatConvert(), MatDuplicate()
2571: @*/
2572: PetscErrorCode MatCopy(Mat A,Mat B,MatStructure str)
2573: {
2580: MatPreallocated(A);
2582: MatPreallocated(B);
2584: if (!A->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2585: if (A->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2586: if (A->M != B->M || A->N != B->N) SETERRQ4(PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim (%D,%D) (%D,%D)",A->M,B->M,
2587: A->N,B->N);
2589: PetscLogEventBegin(MAT_Copy,A,B,0,0);
2590: if (A->ops->copy) {
2591: (*A->ops->copy)(A,B,str);
2592: } else { /* generic conversion */
2593: MatCopy_Basic(A,B,str);
2594: }
2595: if (A->mapping) {
2596: if (B->mapping) {ISLocalToGlobalMappingDestroy(B->mapping);B->mapping = 0;}
2597: MatSetLocalToGlobalMapping(B,A->mapping);
2598: }
2599: if (A->bmapping) {
2600: if (B->bmapping) {ISLocalToGlobalMappingDestroy(B->bmapping);B->bmapping = 0;}
2601: MatSetLocalToGlobalMappingBlock(B,A->mapping);
2602: }
2603: PetscLogEventEnd(MAT_Copy,A,B,0,0);
2604: PetscObjectIncreaseState((PetscObject)B);
2605: return(0);
2606: }
2608: #include petscsys.h
2609: PetscTruth MatConvertRegisterAllCalled = PETSC_FALSE;
2610: PetscFList MatConvertList = 0;
2614: /*@C
2615: MatConvertRegister - Allows one to register a routine that converts a sparse matrix
2616: from one format to another.
2618: Not Collective
2620: Input Parameters:
2621: + type - the type of matrix (defined in include/petscmat.h), for example, MATSEQAIJ.
2622: - Converter - the function that reads the matrix from the binary file.
2624: Level: developer
2626: .seealso: MatConvertRegisterAll(), MatConvert()
2628: @*/
2629: PetscErrorCode MatConvertRegister(const char sname[],const char path[],const char name[],PetscErrorCode (*function)(Mat,MatType,Mat*))
2630: {
2632: char fullname[PETSC_MAX_PATH_LEN];
2635: PetscFListConcat(path,name,fullname);
2636: PetscFListAdd(&MatConvertList,sname,fullname,(void (*)(void))function);
2637: return(0);
2638: }
2642: /*@C
2643: MatConvert - Converts a matrix to another matrix, either of the same
2644: or different type.
2646: Collective on Mat
2648: Input Parameters:
2649: + mat - the matrix
2650: - newtype - new matrix type. Use MATSAME to create a new matrix of the
2651: same type as the original matrix.
2653: Output Parameter:
2654: . M - pointer to place new matrix
2656: Notes:
2657: MatConvert() first creates a new matrix and then copies the data from
2658: the first matrix. A related routine is MatCopy(), which copies the matrix
2659: entries of one matrix to another already existing matrix context.
2661: Level: intermediate
2663: Concepts: matrices^converting between storage formats
2665: .seealso: MatCopy(), MatDuplicate()
2666: @*/
2667: PetscErrorCode MatConvert(Mat mat,const MatType newtype,Mat *M)
2668: {
2670: PetscTruth sametype,issame,flg;
2671: char convname[256],mtype[256];
2676: MatPreallocated(mat);
2678: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2679: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2681: PetscOptionsGetString(PETSC_NULL,"-matconvert_type",mtype,256,&flg);
2682: if (flg) {
2683: newtype = mtype;
2684: }
2685: PetscLogEventBegin(MAT_Convert,mat,0,0,0);
2686:
2687: PetscTypeCompare((PetscObject)mat,newtype,&sametype);
2688: PetscStrcmp(newtype,"same",&issame);
2689: if ((sametype || issame) && mat->ops->duplicate) {
2690: (*mat->ops->duplicate)(mat,MAT_COPY_VALUES,M);
2691: } else {
2692: PetscErrorCode (*conv)(Mat,const MatType,Mat*)=PETSC_NULL;
2693: /*
2694: Order of precedence:
2695: 1) See if a specialized converter is known to the current matrix.
2696: 2) See if a specialized converter is known to the desired matrix class.
2697: 3) See if a good general converter is registered for the desired class
2698: (as of 6/27/03 only MATMPIADJ falls into this category).
2699: 4) See if a good general converter is known for the current matrix.
2700: 5) Use a really basic converter.
2701: */
2702: PetscStrcpy(convname,"MatConvert_");
2703: PetscStrcat(convname,mat->type_name);
2704: PetscStrcat(convname,"_");
2705: PetscStrcat(convname,newtype);
2706: PetscStrcat(convname,"_C");
2707: PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);
2708: if (!conv) {
2709: Mat B;
2710: MatCreate(mat->comm,0,0,0,0,&B);
2711: MatSetType(B,newtype);
2712: PetscObjectQueryFunction((PetscObject)B,convname,(void (**)(void))&conv);
2713: MatDestroy(B);
2714: if (!conv) {
2715: if (!MatConvertRegisterAllCalled) {
2716: MatConvertRegisterAll(PETSC_NULL);
2717: }
2718: PetscFListFind(mat->comm,MatConvertList,newtype,(void(**)(void))&conv);
2719: if (!conv) {
2720: if (mat->ops->convert) {
2721: conv = mat->ops->convert;
2722: } else {
2723: conv = MatConvert_Basic;
2724: }
2725: }
2726: }
2727: }
2728: (*conv)(mat,newtype,M);
2729: }
2730: PetscLogEventEnd(MAT_Convert,mat,0,0,0);
2731: PetscObjectIncreaseState((PetscObject)*M);
2732: return(0);
2733: }
2738: /*@C
2739: MatDuplicate - Duplicates a matrix including the non-zero structure.
2741: Collective on Mat
2743: Input Parameters:
2744: + mat - the matrix
2745: - op - either MAT_DO_NOT_COPY_VALUES or MAT_COPY_VALUES, cause it to copy nonzero
2746: values as well or not
2748: Output Parameter:
2749: . M - pointer to place new matrix
2751: Level: intermediate
2753: Concepts: matrices^duplicating
2755: .seealso: MatCopy(), MatConvert()
2756: @*/
2757: PetscErrorCode MatDuplicate(Mat mat,MatDuplicateOption op,Mat *M)
2758: {
2764: MatPreallocated(mat);
2766: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2767: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2769: *M = 0;
2770: PetscLogEventBegin(MAT_Convert,mat,0,0,0);
2771: if (!mat->ops->duplicate) {
2772: SETERRQ(PETSC_ERR_SUP,"Not written for this matrix type");
2773: }
2774: (*mat->ops->duplicate)(mat,op,M);
2775: if (mat->mapping) {
2776: MatSetLocalToGlobalMapping(*M,mat->mapping);
2777: }
2778: if (mat->bmapping) {
2779: MatSetLocalToGlobalMappingBlock(*M,mat->mapping);
2780: }
2781: PetscLogEventEnd(MAT_Convert,mat,0,0,0);
2782: PetscObjectIncreaseState((PetscObject)*M);
2783: return(0);
2784: }
2788: /*@
2789: MatGetDiagonal - Gets the diagonal of a matrix.
2791: Collective on Mat and Vec
2793: Input Parameters:
2794: + mat - the matrix
2795: - v - the vector for storing the diagonal
2797: Output Parameter:
2798: . v - the diagonal of the matrix
2800: Notes:
2801: For the SeqAIJ matrix format, this routine may also be called
2802: on a LU factored matrix; in that case it routines the reciprocal of
2803: the diagonal entries in U. It returns the entries permuted by the
2804: row and column permutation used during the symbolic factorization.
2806: Level: intermediate
2808: Concepts: matrices^accessing diagonals
2810: .seealso: MatGetRow(), MatGetSubmatrices(), MatGetSubmatrix(), MatGetRowMax()
2811: @*/
2812: PetscErrorCode MatGetDiagonal(Mat mat,Vec v)
2813: {
2819: MatPreallocated(mat);
2821: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2822: if (!mat->ops->getdiagonal) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2824: (*mat->ops->getdiagonal)(mat,v);
2825: PetscObjectIncreaseState((PetscObject)v);
2826: return(0);
2827: }
2831: /*@
2832: MatGetRowMax - Gets the maximum value (in absolute value) of each
2833: row of the matrix
2835: Collective on Mat and Vec
2837: Input Parameters:
2838: . mat - the matrix
2840: Output Parameter:
2841: . v - the vector for storing the maximums
2843: Level: intermediate
2845: Concepts: matrices^getting row maximums
2847: .seealso: MatGetDiagonal(), MatGetSubmatrices(), MatGetSubmatrix()
2848: @*/
2849: PetscErrorCode MatGetRowMax(Mat mat,Vec v)
2850: {
2856: MatPreallocated(mat);
2858: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2859: if (!mat->ops->getrowmax) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2861: (*mat->ops->getrowmax)(mat,v);
2862: PetscObjectIncreaseState((PetscObject)v);
2863: return(0);
2864: }
2868: /*@C
2869: MatTranspose - Computes an in-place or out-of-place transpose of a matrix.
2871: Collective on Mat
2873: Input Parameter:
2874: . mat - the matrix to transpose
2876: Output Parameters:
2877: . B - the transpose (or pass in PETSC_NULL for an in-place transpose)
2879: Level: intermediate
2881: Concepts: matrices^transposing
2883: .seealso: MatMultTranspose(), MatMultTransposeAdd(), MatIsTranspose()
2884: @*/
2885: PetscErrorCode MatTranspose(Mat mat,Mat *B)
2886: {
2892: MatPreallocated(mat);
2893: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2894: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2895: if (!mat->ops->transpose) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2897: PetscLogEventBegin(MAT_Transpose,mat,0,0,0);
2898: (*mat->ops->transpose)(mat,B);
2899: PetscLogEventEnd(MAT_Transpose,mat,0,0,0);
2900: if (B) {PetscObjectIncreaseState((PetscObject)*B);}
2901: return(0);
2902: }
2906: /*@C
2907: MatIsTranspose - Test whether a matrix is another one's transpose,
2908: or its own, in which case it tests symmetry.
2910: Collective on Mat
2912: Input Parameter:
2913: + A - the matrix to test
2914: - B - the matrix to test against, this can equal the first parameter
2916: Output Parameters:
2917: . flg - the result
2919: Notes:
2920: Only available for SeqAIJ/MPIAIJ matrices. The sequential algorithm
2921: has a running time of the order of the number of nonzeros; the parallel
2922: test involves parallel copies of the block-offdiagonal parts of the matrix.
2924: Level: intermediate
2926: Concepts: matrices^transposing, matrix^symmetry
2928: .seealso: MatTranspose(), MatIsSymmetric(), MatIsHermitian()
2929: @*/
2930: PetscErrorCode MatIsTranspose(Mat A,Mat B,PetscReal tol,PetscTruth *flg)
2931: {
2932: PetscErrorCode ierr,(*f)(Mat,Mat,PetscReal,PetscTruth*),(*g)(Mat,Mat,PetscReal,PetscTruth*);
2938: PetscObjectQueryFunction((PetscObject)A,"MatIsTranspose_C",(void (**)(void))&f);
2939: PetscObjectQueryFunction((PetscObject)B,"MatIsTranspose_C",(void (**)(void))&g);
2940: if (f && g) {
2941: if (f==g) {
2942: (*f)(A,B,tol,flg);
2943: } else {
2944: SETERRQ(PETSC_ERR_ARG_NOTSAMETYPE,"Matrices do not have the same comparator for symmetry test");
2945: }
2946: }
2947: return(0);
2948: }
2952: /*@C
2953: MatPermute - Creates a new matrix with rows and columns permuted from the
2954: original.
2956: Collective on Mat
2958: Input Parameters:
2959: + mat - the matrix to permute
2960: . row - row permutation, each processor supplies only the permutation for its rows
2961: - col - column permutation, each processor needs the entire column permutation, that is
2962: this is the same size as the total number of columns in the matrix
2964: Output Parameters:
2965: . B - the permuted matrix
2967: Level: advanced
2969: Concepts: matrices^permuting
2971: .seealso: MatGetOrdering()
2972: @*/
2973: PetscErrorCode MatPermute(Mat mat,IS row,IS col,Mat *B)
2974: {
2980: MatPreallocated(mat);
2984: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2985: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2986: if (!mat->ops->permute) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
2987: (*mat->ops->permute)(mat,row,col,B);
2988: PetscObjectIncreaseState((PetscObject)*B);
2989: return(0);
2990: }
2994: /*@C
2995: MatPermuteSparsify - Creates a new matrix with rows and columns permuted from the
2996: original and sparsified to the prescribed tolerance.
2998: Collective on Mat
3000: Input Parameters:
3001: + A - The matrix to permute
3002: . band - The half-bandwidth of the sparsified matrix, or PETSC_DECIDE
3003: . frac - The half-bandwidth as a fraction of the total size, or 0.0
3004: . tol - The drop tolerance
3005: . rowp - The row permutation
3006: - colp - The column permutation
3008: Output Parameter:
3009: . B - The permuted, sparsified matrix
3011: Level: advanced
3013: Note:
3014: The default behavior (band = PETSC_DECIDE and frac = 0.0) is to
3015: restrict the half-bandwidth of the resulting matrix to 5% of the
3016: total matrix size.
3018: .keywords: matrix, permute, sparsify
3020: .seealso: MatGetOrdering(), MatPermute()
3021: @*/
3022: PetscErrorCode MatPermuteSparsify(Mat A, PetscInt band, PetscReal frac, PetscReal tol, IS rowp, IS colp, Mat *B)
3023: {
3024: IS irowp, icolp;
3025: PetscInt *rows, *cols;
3026: PetscInt M, N, locRowStart, locRowEnd;
3027: PetscInt nz, newNz;
3028: const PetscInt *cwork;
3029: PetscInt *cnew;
3030: const PetscScalar *vwork;
3031: PetscScalar *vnew;
3032: PetscInt bw, issize;
3033: PetscInt row, locRow, newRow, col, newCol;
3034: PetscErrorCode ierr;
3041: if (!A->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Not for unassembled matrix");
3042: if (A->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Not for factored matrix");
3043: if (!A->ops->permutesparsify) {
3044: MatGetSize(A, &M, &N);
3045: MatGetOwnershipRange(A, &locRowStart, &locRowEnd);
3046: ISGetSize(rowp, &issize);
3047: if (issize != M) SETERRQ2(PETSC_ERR_ARG_WRONG, "Wrong size %D for row permutation, should be %D", issize, M);
3048: ISGetSize(colp, &issize);
3049: if (issize != N) SETERRQ2(PETSC_ERR_ARG_WRONG, "Wrong size %D for column permutation, should be %D", issize, N);
3050: ISInvertPermutation(rowp, 0, &irowp);
3051: ISGetIndices(irowp, &rows);
3052: ISInvertPermutation(colp, 0, &icolp);
3053: ISGetIndices(icolp, &cols);
3054: PetscMalloc(N * sizeof(PetscInt), &cnew);
3055: PetscMalloc(N * sizeof(PetscScalar), &vnew);
3057: /* Setup bandwidth to include */
3058: if (band == PETSC_DECIDE) {
3059: if (frac <= 0.0)
3060: bw = (PetscInt) (M * 0.05);
3061: else
3062: bw = (PetscInt) (M * frac);
3063: } else {
3064: if (band <= 0) SETERRQ(PETSC_ERR_ARG_WRONG, "Bandwidth must be a positive integer");
3065: bw = band;
3066: }
3068: /* Put values into new matrix */
3069: MatDuplicate(A, MAT_DO_NOT_COPY_VALUES, B);
3070: for(row = locRowStart, locRow = 0; row < locRowEnd; row++, locRow++) {
3071: MatGetRow(A, row, &nz, &cwork, &vwork);
3072: newRow = rows[locRow]+locRowStart;
3073: for(col = 0, newNz = 0; col < nz; col++) {
3074: newCol = cols[cwork[col]];
3075: if ((newCol >= newRow - bw) && (newCol < newRow + bw) && (PetscAbsScalar(vwork[col]) >= tol)) {
3076: cnew[newNz] = newCol;
3077: vnew[newNz] = vwork[col];
3078: newNz++;
3079: }
3080: }
3081: MatSetValues(*B, 1, &newRow, newNz, cnew, vnew, INSERT_VALUES);
3082: MatRestoreRow(A, row, &nz, &cwork, &vwork);
3083: }
3084: PetscFree(cnew);
3085: PetscFree(vnew);
3086: MatAssemblyBegin(*B, MAT_FINAL_ASSEMBLY);
3087: MatAssemblyEnd(*B, MAT_FINAL_ASSEMBLY);
3088: ISRestoreIndices(irowp, &rows);
3089: ISRestoreIndices(icolp, &cols);
3090: ISDestroy(irowp);
3091: ISDestroy(icolp);
3092: } else {
3093: (*A->ops->permutesparsify)(A, band, frac, tol, rowp, colp, B);
3094: }
3095: PetscObjectIncreaseState((PetscObject)*B);
3096: return(0);
3097: }
3101: /*@
3102: MatEqual - Compares two matrices.
3104: Collective on Mat
3106: Input Parameters:
3107: + A - the first matrix
3108: - B - the second matrix
3110: Output Parameter:
3111: . flg - PETSC_TRUE if the matrices are equal; PETSC_FALSE otherwise.
3113: Level: intermediate
3115: Concepts: matrices^equality between
3116: @*/
3117: PetscErrorCode MatEqual(Mat A,Mat B,PetscTruth *flg)
3118: {
3125: MatPreallocated(A);
3127: MatPreallocated(B);
3130: if (!A->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3131: if (!B->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3132: if (A->M != B->M || A->N != B->N) SETERRQ4(PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim %D %D %D %D",A->M,B->M,A->N,B->N);
3133: if (!A->ops->equal) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",A->type_name);
3134: if (!B->ops->equal) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",B->type_name);
3135: if (A->ops->equal != B->ops->equal) SETERRQ2(PETSC_ERR_ARG_INCOMP,"A is type: %s\nB is type: %s",A->type_name,B->type_name);
3136: (*A->ops->equal)(A,B,flg);
3137: return(0);
3138: }
3142: /*@
3143: MatDiagonalScale - Scales a matrix on the left and right by diagonal
3144: matrices that are stored as vectors. Either of the two scaling
3145: matrices can be PETSC_NULL.
3147: Collective on Mat
3149: Input Parameters:
3150: + mat - the matrix to be scaled
3151: . l - the left scaling vector (or PETSC_NULL)
3152: - r - the right scaling vector (or PETSC_NULL)
3154: Notes:
3155: MatDiagonalScale() computes A = LAR, where
3156: L = a diagonal matrix (stored as a vector), R = a diagonal matrix (stored as a vector)
3158: Level: intermediate
3160: Concepts: matrices^diagonal scaling
3161: Concepts: diagonal scaling of matrices
3163: .seealso: MatScale()
3164: @*/
3165: PetscErrorCode MatDiagonalScale(Mat mat,Vec l,Vec r)
3166: {
3172: MatPreallocated(mat);
3173: if (!mat->ops->diagonalscale) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
3176: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3177: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3179: PetscLogEventBegin(MAT_Scale,mat,0,0,0);
3180: (*mat->ops->diagonalscale)(mat,l,r);
3181: PetscLogEventEnd(MAT_Scale,mat,0,0,0);
3182: PetscObjectIncreaseState((PetscObject)mat);
3183: return(0);
3184: }
3188: /*@
3189: MatScale - Scales all elements of a matrix by a given number.
3191: Collective on Mat
3193: Input Parameters:
3194: + mat - the matrix to be scaled
3195: - a - the scaling value
3197: Output Parameter:
3198: . mat - the scaled matrix
3200: Level: intermediate
3202: Concepts: matrices^scaling all entries
3204: .seealso: MatDiagonalScale()
3205: @*/
3206: PetscErrorCode MatScale(const PetscScalar *a,Mat mat)
3207: {
3214: MatPreallocated(mat);
3215: if (!mat->ops->scale) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
3216: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3217: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3219: PetscLogEventBegin(MAT_Scale,mat,0,0,0);
3220: (*mat->ops->scale)(a,mat);
3221: PetscLogEventEnd(MAT_Scale,mat,0,0,0);
3222: PetscObjectIncreaseState((PetscObject)mat);
3223: return(0);
3224: }
3228: /*@
3229: MatNorm - Calculates various norms of a matrix.
3231: Collective on Mat
3233: Input Parameters:
3234: + mat - the matrix
3235: - type - the type of norm, NORM_1, NORM_FROBENIUS, NORM_INFINITY
3237: Output Parameters:
3238: . nrm - the resulting norm
3240: Level: intermediate
3242: Concepts: matrices^norm
3243: Concepts: norm^of matrix
3244: @*/
3245: PetscErrorCode MatNorm(Mat mat,NormType type,PetscReal *nrm)
3246: {
3252: MatPreallocated(mat);
3255: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3256: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3257: if (!mat->ops->norm) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
3258: (*mat->ops->norm)(mat,type,nrm);
3259: return(0);
3260: }
3262: /*
3263: This variable is used to prevent counting of MatAssemblyBegin() that
3264: are called from within a MatAssemblyEnd().
3265: */
3266: static PetscInt MatAssemblyEnd_InUse = 0;
3269: /*@
3270: MatAssemblyBegin - Begins assembling the matrix. This routine should
3271: be called after completing all calls to MatSetValues().
3273: Collective on Mat
3275: Input Parameters:
3276: + mat - the matrix
3277: - type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY
3278:
3279: Notes:
3280: MatSetValues() generally caches the values. The matrix is ready to
3281: use only after MatAssemblyBegin() and MatAssemblyEnd() have been called.
3282: Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES
3283: in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before
3284: using the matrix.
3286: Level: beginner
3288: Concepts: matrices^assembling
3290: .seealso: MatAssemblyEnd(), MatSetValues(), MatAssembled()
3291: @*/
3292: PetscErrorCode MatAssemblyBegin(Mat mat,MatAssemblyType type)
3293: {
3299: MatPreallocated(mat);
3300: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix.\nDid you forget to call MatSetUnfactored()?");
3301: if (mat->assembled) {
3302: mat->was_assembled = PETSC_TRUE;
3303: mat->assembled = PETSC_FALSE;
3304: }
3305: if (!MatAssemblyEnd_InUse) {
3306: PetscLogEventBegin(MAT_AssemblyBegin,mat,0,0,0);
3307: if (mat->ops->assemblybegin){(*mat->ops->assemblybegin)(mat,type);}
3308: PetscLogEventEnd(MAT_AssemblyBegin,mat,0,0,0);
3309: } else {
3310: if (mat->ops->assemblybegin){(*mat->ops->assemblybegin)(mat,type);}
3311: }
3312: return(0);
3313: }
3317: /*@
3318: MatAssembled - Indicates if a matrix has been assembled and is ready for
3319: use; for example, in matrix-vector product.
3321: Collective on Mat
3323: Input Parameter:
3324: . mat - the matrix
3326: Output Parameter:
3327: . assembled - PETSC_TRUE or PETSC_FALSE
3329: Level: advanced
3331: Concepts: matrices^assembled?
3333: .seealso: MatAssemblyEnd(), MatSetValues(), MatAssemblyBegin()
3334: @*/
3335: PetscErrorCode MatAssembled(Mat mat,PetscTruth *assembled)
3336: {
3340: MatPreallocated(mat);
3342: *assembled = mat->assembled;
3343: return(0);
3344: }
3348: /*
3349: Processes command line options to determine if/how a matrix
3350: is to be viewed. Called by MatAssemblyEnd() and MatLoad().
3351: */
3352: PetscErrorCode MatView_Private(Mat mat)
3353: {
3354: PetscErrorCode ierr;
3355: PetscTruth flg;
3356: static PetscTruth incall = PETSC_FALSE;
3359: if (incall) return(0);
3360: incall = PETSC_TRUE;
3361: PetscOptionsBegin(mat->comm,mat->prefix,"Matrix Options","Mat");
3362: PetscOptionsName("-mat_view_info","Information on matrix size","MatView",&flg);
3363: if (flg) {
3364: PetscViewerPushFormat(PETSC_VIEWER_STDOUT_(mat->comm),PETSC_VIEWER_ASCII_INFO);
3365: MatView(mat,PETSC_VIEWER_STDOUT_(mat->comm));
3366: PetscViewerPopFormat(PETSC_VIEWER_STDOUT_(mat->comm));
3367: }
3368: PetscOptionsName("-mat_view_info_detailed","Nonzeros in the matrix","MatView",&flg);
3369: if (flg) {
3370: PetscViewerPushFormat(PETSC_VIEWER_STDOUT_(mat->comm),PETSC_VIEWER_ASCII_INFO_DETAIL);
3371: MatView(mat,PETSC_VIEWER_STDOUT_(mat->comm));
3372: PetscViewerPopFormat(PETSC_VIEWER_STDOUT_(mat->comm));
3373: }
3374: PetscOptionsName("-mat_view","Print matrix to stdout","MatView",&flg);
3375: if (flg) {
3376: MatView(mat,PETSC_VIEWER_STDOUT_(mat->comm));
3377: }
3378: PetscOptionsName("-mat_view_matlab","Print matrix to stdout in a format Matlab can read","MatView",&flg);
3379: if (flg) {
3380: PetscViewerPushFormat(PETSC_VIEWER_STDOUT_(mat->comm),PETSC_VIEWER_ASCII_MATLAB);
3381: MatView(mat,PETSC_VIEWER_STDOUT_(mat->comm));
3382: PetscViewerPopFormat(PETSC_VIEWER_STDOUT_(mat->comm));
3383: }
3384: PetscOptionsName("-mat_view_socket","Send matrix to socket (can be read from matlab)","MatView",&flg);
3385: if (flg) {
3386: MatView(mat,PETSC_VIEWER_SOCKET_(mat->comm));
3387: PetscViewerFlush(PETSC_VIEWER_SOCKET_(mat->comm));
3388: }
3389: PetscOptionsName("-mat_view_binary","Save matrix to file in binary format","MatView",&flg);
3390: if (flg) {
3391: MatView(mat,PETSC_VIEWER_BINARY_(mat->comm));
3392: PetscViewerFlush(PETSC_VIEWER_BINARY_(mat->comm));
3393: }
3394: PetscOptionsEnd();
3395: /* cannot have inside PetscOptionsBegin() because uses PetscOptionsBegin() */
3396: PetscOptionsHasName(mat->prefix,"-mat_view_draw",&flg);
3397: if (flg) {
3398: PetscOptionsHasName(mat->prefix,"-mat_view_contour",&flg);
3399: if (flg) {
3400: PetscViewerPushFormat(PETSC_VIEWER_DRAW_(mat->comm),PETSC_VIEWER_DRAW_CONTOUR);
3401: }
3402: MatView(mat,PETSC_VIEWER_DRAW_(mat->comm));
3403: PetscViewerFlush(PETSC_VIEWER_DRAW_(mat->comm));
3404: if (flg) {
3405: PetscViewerPopFormat(PETSC_VIEWER_DRAW_(mat->comm));
3406: }
3407: }
3408: incall = PETSC_FALSE;
3409: return(0);
3410: }
3414: /*@
3415: MatAssemblyEnd - Completes assembling the matrix. This routine should
3416: be called after MatAssemblyBegin().
3418: Collective on Mat
3420: Input Parameters:
3421: + mat - the matrix
3422: - type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY
3424: Options Database Keys:
3425: + -mat_view_info - Prints info on matrix at conclusion of MatEndAssembly()
3426: . -mat_view_info_detailed - Prints more detailed info
3427: . -mat_view - Prints matrix in ASCII format
3428: . -mat_view_matlab - Prints matrix in Matlab format
3429: . -mat_view_draw - PetscDraws nonzero structure of matrix, using MatView() and PetscDrawOpenX().
3430: . -display <name> - Sets display name (default is host)
3431: . -draw_pause <sec> - Sets number of seconds to pause after display
3432: . -mat_view_socket - Sends matrix to socket, can be accessed from Matlab (see users manual)
3433: . -viewer_socket_machine <machine>
3434: . -viewer_socket_port <port>
3435: . -mat_view_binary - save matrix to file in binary format
3436: - -viewer_binary_filename <name>
3438: Notes:
3439: MatSetValues() generally caches the values. The matrix is ready to
3440: use only after MatAssemblyBegin() and MatAssemblyEnd() have been called.
3441: Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES
3442: in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before
3443: using the matrix.
3445: Level: beginner
3447: .seealso: MatAssemblyBegin(), MatSetValues(), PetscDrawOpenX(), MatView(), MatAssembled(), PetscViewerSocketOpen()
3448: @*/
3449: PetscErrorCode MatAssemblyEnd(Mat mat,MatAssemblyType type)
3450: {
3451: PetscErrorCode ierr;
3452: static PetscInt inassm = 0;
3453: PetscTruth flg;
3458: MatPreallocated(mat);
3460: inassm++;
3461: MatAssemblyEnd_InUse++;
3462: if (MatAssemblyEnd_InUse == 1) { /* Do the logging only the first time through */
3463: PetscLogEventBegin(MAT_AssemblyEnd,mat,0,0,0);
3464: if (mat->ops->assemblyend) {
3465: (*mat->ops->assemblyend)(mat,type);
3466: }
3467: PetscLogEventEnd(MAT_AssemblyEnd,mat,0,0,0);
3468: } else {
3469: if (mat->ops->assemblyend) {
3470: (*mat->ops->assemblyend)(mat,type);
3471: }
3472: }
3474: /* Flush assembly is not a true assembly */
3475: if (type != MAT_FLUSH_ASSEMBLY) {
3476: mat->assembled = PETSC_TRUE; mat->num_ass++;
3477: }
3478: mat->insertmode = NOT_SET_VALUES;
3479: MatAssemblyEnd_InUse--;
3480: PetscObjectIncreaseState((PetscObject)mat);
3481: if (!mat->symmetric_eternal) {
3482: mat->symmetric_set = PETSC_FALSE;
3483: mat->hermitian_set = PETSC_FALSE;
3484: mat->structurally_symmetric_set = PETSC_FALSE;
3485: }
3486: if (inassm == 1 && type != MAT_FLUSH_ASSEMBLY) {
3487: MatView_Private(mat);
3488: PetscOptionsHasName(mat->prefix,"-mat_is_symmetric",&flg);
3489: if (flg) {
3490: PetscReal tol = 0.0;
3491: PetscOptionsGetReal(mat->prefix,"-mat_is_symmetric",&tol,PETSC_NULL);
3492: MatIsSymmetric(mat,tol,&flg);
3493: if (flg) {
3494: PetscPrintf(mat->comm,"Matrix is symmetric (tolerance %g)\n",tol);
3495: } else {
3496: PetscPrintf(mat->comm,"Matrix is not symmetric (tolerance %g)\n",tol);
3497: }
3498: }
3499: }
3500: inassm--;
3501: PetscOptionsHasName(mat->prefix,"-help",&flg);
3502: if (flg) {
3503: MatPrintHelp(mat);
3504: }
3505: return(0);
3506: }
3511: /*@
3512: MatCompress - Tries to store the matrix in as little space as
3513: possible. May fail if memory is already fully used, since it
3514: tries to allocate new space.
3516: Collective on Mat
3518: Input Parameters:
3519: . mat - the matrix
3521: Level: advanced
3523: @*/
3524: PetscErrorCode MatCompress(Mat mat)
3525: {
3531: MatPreallocated(mat);
3532: if (mat->ops->compress) {(*mat->ops->compress)(mat);}
3533: return(0);
3534: }
3538: /*@
3539: MatSetOption - Sets a parameter option for a matrix. Some options
3540: may be specific to certain storage formats. Some options
3541: determine how values will be inserted (or added). Sorted,
3542: row-oriented input will generally assemble the fastest. The default
3543: is row-oriented, nonsorted input.
3545: Collective on Mat
3547: Input Parameters:
3548: + mat - the matrix
3549: - option - the option, one of those listed below (and possibly others),
3550: e.g., MAT_ROWS_SORTED, MAT_NEW_NONZERO_LOCATION_ERR
3552: Options Describing Matrix Structure:
3553: + MAT_SYMMETRIC - symmetric in terms of both structure and value
3554: . MAT_HERMITIAN - transpose is the complex conjugation
3555: . MAT_STRUCTURALLY_SYMMETRIC - symmetric nonzero structure
3556: . MAT_NOT_SYMMETRIC - not symmetric in value
3557: . MAT_NOT_HERMITIAN - transpose is not the complex conjugation
3558: . MAT_NOT_STRUCTURALLY_SYMMETRIC - not symmetric nonzero structure
3559: . MAT_SYMMETRY_ETERNAL - if you would like the symmetry/Hermitian flag
3560: you set to be kept with all future use of the matrix
3561: including after MatAssemblyBegin/End() which could
3562: potentially change the symmetry structure, i.e. you
3563: KNOW the matrix will ALWAYS have the property you set.
3564: - MAT_NOT_SYMMETRY_ETERNAL - if MatAssemblyBegin/End() is called then the
3565: flags you set will be dropped (in case potentially
3566: the symmetry etc was lost).
3568: Options For Use with MatSetValues():
3569: Insert a logically dense subblock, which can be
3570: + MAT_ROW_ORIENTED - row-oriented (default)
3571: . MAT_COLUMN_ORIENTED - column-oriented
3572: . MAT_ROWS_SORTED - sorted by row
3573: . MAT_ROWS_UNSORTED - not sorted by row (default)
3574: . MAT_COLUMNS_SORTED - sorted by column
3575: - MAT_COLUMNS_UNSORTED - not sorted by column (default)
3577: Not these options reflect the data you pass in with MatSetValues(); it has
3578: nothing to do with how the data is stored internally in the matrix
3579: data structure.
3581: When (re)assembling a matrix, we can restrict the input for
3582: efficiency/debugging purposes. These options include
3583: + MAT_NO_NEW_NONZERO_LOCATIONS - additional insertions will not be
3584: allowed if they generate a new nonzero
3585: . MAT_YES_NEW_NONZERO_LOCATIONS - additional insertions will be allowed
3586: . MAT_NO_NEW_DIAGONALS - additional insertions will not be allowed if
3587: they generate a nonzero in a new diagonal (for block diagonal format only)
3588: . MAT_YES_NEW_DIAGONALS - new diagonals will be allowed (for block diagonal format only)
3589: . MAT_IGNORE_OFF_PROC_ENTRIES - drops off-processor entries
3590: . MAT_NEW_NONZERO_LOCATION_ERR - generates an error for new matrix entry
3591: - MAT_USE_HASH_TABLE - uses a hash table to speed up matrix assembly
3593: Notes:
3594: Some options are relevant only for particular matrix types and
3595: are thus ignored by others. Other options are not supported by
3596: certain matrix types and will generate an error message if set.
3598: If using a Fortran 77 module to compute a matrix, one may need to
3599: use the column-oriented option (or convert to the row-oriented
3600: format).
3602: MAT_NO_NEW_NONZERO_LOCATIONS indicates that any add or insertion
3603: that would generate a new entry in the nonzero structure is instead
3604: ignored. Thus, if memory has not alredy been allocated for this particular
3605: data, then the insertion is ignored. For dense matrices, in which
3606: the entire array is allocated, no entries are ever ignored.
3607: Set after the first MatAssemblyEnd()
3609: MAT_NEW_NONZERO_LOCATION_ERR indicates that any add or insertion
3610: that would generate a new entry in the nonzero structure instead produces
3611: an error. (Currently supported for AIJ and BAIJ formats only.)
3612: This is a useful flag when using SAME_NONZERO_PATTERN in calling
3613: KSPSetOperators() to ensure that the nonzero pattern truely does
3614: remain unchanged. Set after the first MatAssemblyEnd()
3616: MAT_NEW_NONZERO_ALLOCATION_ERR indicates that any add or insertion
3617: that would generate a new entry that has not been preallocated will
3618: instead produce an error. (Currently supported for AIJ and BAIJ formats
3619: only.) This is a useful flag when debugging matrix memory preallocation.
3621: MAT_IGNORE_OFF_PROC_ENTRIES indicates entries destined for
3622: other processors should be dropped, rather than stashed.
3623: This is useful if you know that the "owning" processor is also
3624: always generating the correct matrix entries, so that PETSc need
3625: not transfer duplicate entries generated on another processor.
3626:
3627: MAT_USE_HASH_TABLE indicates that a hash table be used to improve the
3628: searches during matrix assembly. When this flag is set, the hash table
3629: is created during the first Matrix Assembly. This hash table is
3630: used the next time through, during MatSetVaules()/MatSetVaulesBlocked()
3631: to improve the searching of indices. MAT_NO_NEW_NONZERO_LOCATIONS flag
3632: should be used with MAT_USE_HASH_TABLE flag. This option is currently
3633: supported by MATMPIBAIJ format only.
3635: MAT_KEEP_ZEROED_ROWS indicates when MatZeroRows() is called the zeroed entries
3636: are kept in the nonzero structure
3638: MAT_IGNORE_ZERO_ENTRIES - for AIJ matrices this will stop zero values from creating
3639: a zero location in the matrix
3641: MAT_USE_INODES - indicates using inode version of the code - works with AIJ and
3642: ROWBS matrix types
3644: MAT_DO_NOT_USE_INODES - indicates not using inode version of the code - works
3645: with AIJ and ROWBS matrix types
3647: Level: intermediate
3649: Concepts: matrices^setting options
3651: @*/
3652: PetscErrorCode MatSetOption(Mat mat,MatOption op)
3653: {
3659: MatPreallocated(mat);
3660: switch (op) {
3661: case MAT_SYMMETRIC:
3662: mat->symmetric = PETSC_TRUE;
3663: mat->structurally_symmetric = PETSC_TRUE;
3664: mat->symmetric_set = PETSC_TRUE;
3665: mat->structurally_symmetric_set = PETSC_TRUE;
3666: break;
3667: case MAT_HERMITIAN:
3668: mat->hermitian = PETSC_TRUE;
3669: mat->structurally_symmetric = PETSC_TRUE;
3670: mat->hermitian_set = PETSC_TRUE;
3671: mat->structurally_symmetric_set = PETSC_TRUE;
3672: break;
3673: case MAT_STRUCTURALLY_SYMMETRIC:
3674: mat->structurally_symmetric = PETSC_TRUE;
3675: mat->structurally_symmetric_set = PETSC_TRUE;
3676: break;
3677: case MAT_NOT_SYMMETRIC:
3678: mat->symmetric = PETSC_FALSE;
3679: mat->symmetric_set = PETSC_TRUE;
3680: break;
3681: case MAT_NOT_HERMITIAN:
3682: mat->hermitian = PETSC_FALSE;
3683: mat->hermitian_set = PETSC_TRUE;
3684: break;
3685: case MAT_NOT_STRUCTURALLY_SYMMETRIC:
3686: mat->structurally_symmetric = PETSC_FALSE;
3687: mat->structurally_symmetric_set = PETSC_TRUE;
3688: break;
3689: case MAT_SYMMETRY_ETERNAL:
3690: mat->symmetric_eternal = PETSC_TRUE;
3691: break;
3692: case MAT_NOT_SYMMETRY_ETERNAL:
3693: mat->symmetric_eternal = PETSC_FALSE;
3694: break;
3695: default:
3696: break;
3697: }
3698: if (mat->ops->setoption) {
3699: (*mat->ops->setoption)(mat,op);
3700: }
3701: return(0);
3702: }
3706: /*@
3707: MatZeroEntries - Zeros all entries of a matrix. For sparse matrices
3708: this routine retains the old nonzero structure.
3710: Collective on Mat
3712: Input Parameters:
3713: . mat - the matrix
3715: Level: intermediate
3717: Concepts: matrices^zeroing
3719: .seealso: MatZeroRows()
3720: @*/
3721: PetscErrorCode MatZeroEntries(Mat mat)
3722: {
3728: MatPreallocated(mat);
3729: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3730: if (mat->insertmode != NOT_SET_VALUES) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for matrices where you have set values but not yet assembled");
3731: if (!mat->ops->zeroentries) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
3733: PetscLogEventBegin(MAT_ZeroEntries,mat,0,0,0);
3734: (*mat->ops->zeroentries)(mat);
3735: PetscLogEventEnd(MAT_ZeroEntries,mat,0,0,0);
3736: PetscObjectIncreaseState((PetscObject)mat);
3737: return(0);
3738: }
3742: /*@C
3743: MatZeroRows - Zeros all entries (except possibly the main diagonal)
3744: of a set of rows of a matrix.
3746: Collective on Mat
3748: Input Parameters:
3749: + mat - the matrix
3750: . is - index set of rows to remove
3751: - diag - pointer to value put in all diagonals of eliminated rows.
3752: Note that diag is not a pointer to an array, but merely a
3753: pointer to a single value.
3755: Notes:
3756: For the AIJ and BAIJ matrix formats this removes the old nonzero structure,
3757: but does not release memory. For the dense and block diagonal
3758: formats this does not alter the nonzero structure.
3760: If the option MatSetOption(mat,MAT_KEEP_ZEROED_ROWS) the nonzero structure
3761: of the matrix is not changed (even for AIJ and BAIJ matrices) the values are
3762: merely zeroed.
3764: The user can set a value in the diagonal entry (or for the AIJ and
3765: row formats can optionally remove the main diagonal entry from the
3766: nonzero structure as well, by passing a null pointer (PETSC_NULL
3767: in C or PETSC_NULL_SCALAR in Fortran) as the final argument).
3769: For the parallel case, all processes that share the matrix (i.e.,
3770: those in the communicator used for matrix creation) MUST call this
3771: routine, regardless of whether any rows being zeroed are owned by
3772: them.
3774: Each processor should list the rows that IT wants zeroed
3776: Level: intermediate
3778: Concepts: matrices^zeroing rows
3780: .seealso: MatZeroEntries(), MatZeroRowsLocal(), MatSetOption()
3781: @*/
3782: PetscErrorCode MatZeroRows(Mat mat,IS is,const PetscScalar *diag)
3783: {
3789: MatPreallocated(mat);
3792: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3793: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3794: if (!mat->ops->zerorows) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
3796: (*mat->ops->zerorows)(mat,is,diag);
3797: MatView_Private(mat);
3798: PetscObjectIncreaseState((PetscObject)mat);
3799: return(0);
3800: }
3804: /*@C
3805: MatZeroRowsLocal - Zeros all entries (except possibly the main diagonal)
3806: of a set of rows of a matrix; using local numbering of rows.
3808: Collective on Mat
3810: Input Parameters:
3811: + mat - the matrix
3812: . is - index set of rows to remove
3813: - diag - pointer to value put in all diagonals of eliminated rows.
3814: Note that diag is not a pointer to an array, but merely a
3815: pointer to a single value.
3817: Notes:
3818: Before calling MatZeroRowsLocal(), the user must first set the
3819: local-to-global mapping by calling MatSetLocalToGlobalMapping().
3821: For the AIJ matrix formats this removes the old nonzero structure,
3822: but does not release memory. For the dense and block diagonal
3823: formats this does not alter the nonzero structure.
3825: If the option MatSetOption(mat,MAT_KEEP_ZEROED_ROWS) the nonzero structure
3826: of the matrix is not changed (even for AIJ and BAIJ matrices) the values are
3827: merely zeroed.
3829: The user can set a value in the diagonal entry (or for the AIJ and
3830: row formats can optionally remove the main diagonal entry from the
3831: nonzero structure as well, by passing a null pointer (PETSC_NULL
3832: in C or PETSC_NULL_SCALAR in Fortran) as the final argument).
3834: Level: intermediate
3836: Concepts: matrices^zeroing
3838: .seealso: MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping
3839: @*/
3840: PetscErrorCode MatZeroRowsLocal(Mat mat,IS is,const PetscScalar *diag)
3841: {
3843: IS newis;
3848: MatPreallocated(mat);
3851: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3852: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3854: if (mat->ops->zerorowslocal) {
3855: (*mat->ops->zerorowslocal)(mat,is,diag);
3856: } else {
3857: if (!mat->mapping) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Need to provide local to global mapping to matrix first");
3858: ISLocalToGlobalMappingApplyIS(mat->mapping,is,&newis);
3859: (*mat->ops->zerorows)(mat,newis,diag);
3860: ISDestroy(newis);
3861: }
3862: PetscObjectIncreaseState((PetscObject)mat);
3863: return(0);
3864: }
3868: /*@
3869: MatGetSize - Returns the numbers of rows and columns in a matrix.
3871: Not Collective
3873: Input Parameter:
3874: . mat - the matrix
3876: Output Parameters:
3877: + m - the number of global rows
3878: - n - the number of global columns
3880: Note: both output parameters can be PETSC_NULL on input.
3882: Level: beginner
3884: Concepts: matrices^size
3886: .seealso: MatGetLocalSize()
3887: @*/
3888: PetscErrorCode MatGetSize(Mat mat,PetscInt *m,PetscInt* n)
3889: {
3892: if (m) *m = mat->M;
3893: if (n) *n = mat->N;
3894: return(0);
3895: }
3899: /*@
3900: MatGetLocalSize - Returns the number of rows and columns in a matrix
3901: stored locally. This information may be implementation dependent, so
3902: use with care.
3904: Not Collective
3906: Input Parameters:
3907: . mat - the matrix
3909: Output Parameters:
3910: + m - the number of local rows
3911: - n - the number of local columns
3913: Note: both output parameters can be PETSC_NULL on input.
3915: Level: beginner
3917: Concepts: matrices^local size
3919: .seealso: MatGetSize()
3920: @*/
3921: PetscErrorCode MatGetLocalSize(Mat mat,PetscInt *m,PetscInt* n)
3922: {
3927: if (m) *m = mat->m;
3928: if (n) *n = mat->n;
3929: return(0);
3930: }
3934: /*@
3935: MatGetOwnershipRange - Returns the range of matrix rows owned by
3936: this processor, assuming that the matrix is laid out with the first
3937: n1 rows on the first processor, the next n2 rows on the second, etc.
3938: For certain parallel layouts this range may not be well defined.
3940: Not Collective
3942: Input Parameters:
3943: . mat - the matrix
3945: Output Parameters:
3946: + m - the global index of the first local row
3947: - n - one more than the global index of the last local row
3949: Note: both output parameters can be PETSC_NULL on input.
3951: Level: beginner
3953: Concepts: matrices^row ownership
3954: @*/
3955: PetscErrorCode MatGetOwnershipRange(Mat mat,PetscInt *m,PetscInt* n)
3956: {
3962: MatPreallocated(mat);
3965: PetscMapGetLocalRange(mat->rmap,m,n);
3966: return(0);
3967: }
3971: /*@
3972: MatILUFactorSymbolic - Performs symbolic ILU factorization of a matrix.
3973: Uses levels of fill only, not drop tolerance. Use MatLUFactorNumeric()
3974: to complete the factorization.
3976: Collective on Mat
3978: Input Parameters:
3979: + mat - the matrix
3980: . row - row permutation
3981: . column - column permutation
3982: - info - structure containing
3983: $ levels - number of levels of fill.
3984: $ expected fill - as ratio of original fill.
3985: $ 1 or 0 - indicating force fill on diagonal (improves robustness for matrices
3986: missing diagonal entries)
3988: Output Parameters:
3989: . fact - new matrix that has been symbolically factored
3991: Notes:
3992: See the users manual for additional information about
3993: choosing the fill factor for better efficiency.
3995: Most users should employ the simplified KSP interface for linear solvers
3996: instead of working directly with matrix algebra routines such as this.
3997: See, e.g., KSPCreate().
3999: Level: developer
4001: Concepts: matrices^symbolic LU factorization
4002: Concepts: matrices^factorization
4003: Concepts: LU^symbolic factorization
4005: .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
4006: MatGetOrdering(), MatFactorInfo
4008: @*/
4009: PetscErrorCode MatILUFactorSymbolic(Mat mat,IS row,IS col,MatFactorInfo *info,Mat *fact)
4010: {
4016: MatPreallocated(mat);
4021: if (info->levels < 0) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Levels of fill negative %D",(PetscInt)info->levels);
4022: if (info->fill < 1.0) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Expected fill less than 1.0 %g",info->fill);
4023: if (!mat->ops->ilufactorsymbolic) SETERRQ1(PETSC_ERR_SUP,"Matrix type %s symbolic ILU",mat->type_name);
4024: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4025: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4027: PetscLogEventBegin(MAT_ILUFactorSymbolic,mat,row,col,0);
4028: (*mat->ops->ilufactorsymbolic)(mat,row,col,info,fact);
4029: PetscLogEventEnd(MAT_ILUFactorSymbolic,mat,row,col,0);
4030: return(0);
4031: }
4035: /*@
4036: MatICCFactorSymbolic - Performs symbolic incomplete
4037: Cholesky factorization for a symmetric matrix. Use
4038: MatCholeskyFactorNumeric() to complete the factorization.
4040: Collective on Mat
4042: Input Parameters:
4043: + mat - the matrix
4044: . perm - row and column permutation
4045: - info - structure containing
4046: $ levels - number of levels of fill.
4047: $ expected fill - as ratio of original fill.
4049: Output Parameter:
4050: . fact - the factored matrix
4052: Notes:
4053: Currently only no-fill factorization is supported.
4055: Most users should employ the simplified KSP interface for linear solvers
4056: instead of working directly with matrix algebra routines such as this.
4057: See, e.g., KSPCreate().
4059: Level: developer
4061: Concepts: matrices^symbolic incomplete Cholesky factorization
4062: Concepts: matrices^factorization
4063: Concepts: Cholsky^symbolic factorization
4065: .seealso: MatCholeskyFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
4066: @*/
4067: PetscErrorCode MatICCFactorSymbolic(Mat mat,IS perm,MatFactorInfo *info,Mat *fact)
4068: {
4074: MatPreallocated(mat);
4078: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4079: if (info->levels < 0) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Levels negative %D",(PetscInt) info->levels);
4080: if (info->fill < 1.0) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Expected fill less than 1.0 %g",info->fill);
4081: if (!mat->ops->iccfactorsymbolic) SETERRQ1(PETSC_ERR_SUP,"Matrix type %s symbolic ICC",mat->type_name);
4082: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4084: PetscLogEventBegin(MAT_ICCFactorSymbolic,mat,perm,0,0);
4085: (*mat->ops->iccfactorsymbolic)(mat,perm,info,fact);
4086: PetscLogEventEnd(MAT_ICCFactorSymbolic,mat,perm,0,0);
4087: return(0);
4088: }
4092: /*@C
4093: MatGetArray - Returns a pointer to the element values in the matrix.
4094: The result of this routine is dependent on the underlying matrix data
4095: structure, and may not even work for certain matrix types. You MUST
4096: call MatRestoreArray() when you no longer need to access the array.
4098: Not Collective
4100: Input Parameter:
4101: . mat - the matrix
4103: Output Parameter:
4104: . v - the location of the values
4107: Fortran Note:
4108: This routine is used differently from Fortran, e.g.,
4109: .vb
4110: Mat mat
4111: PetscScalar mat_array(1)
4112: PetscOffset i_mat
4113: PetscErrorCode ierr
4114: call MatGetArray(mat,mat_array,i_mat,ierr)
4116: C Access first local entry in matrix; note that array is
4117: C treated as one dimensional
4118: value = mat_array(i_mat + 1)
4120: [... other code ...]
4121: call MatRestoreArray(mat,mat_array,i_mat,ierr)
4122: .ve
4124: See the Fortran chapter of the users manual and
4125: petsc/src/mat/examples/tests for details.
4127: Level: advanced
4129: Concepts: matrices^access array
4131: .seealso: MatRestoreArray(), MatGetArrayF90()
4132: @*/
4133: PetscErrorCode MatGetArray(Mat mat,PetscScalar *v[])
4134: {
4140: MatPreallocated(mat);
4142: if (!mat->ops->getarray) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
4143: (*mat->ops->getarray)(mat,v);
4144: return(0);
4145: }
4149: /*@C
4150: MatRestoreArray - Restores the matrix after MatGetArray() has been called.
4152: Not Collective
4154: Input Parameter:
4155: + mat - the matrix
4156: - v - the location of the values
4158: Fortran Note:
4159: This routine is used differently from Fortran, e.g.,
4160: .vb
4161: Mat mat
4162: PetscScalar mat_array(1)
4163: PetscOffset i_mat
4164: PetscErrorCode ierr
4165: call MatGetArray(mat,mat_array,i_mat,ierr)
4167: C Access first local entry in matrix; note that array is
4168: C treated as one dimensional
4169: value = mat_array(i_mat + 1)
4171: [... other code ...]
4172: call MatRestoreArray(mat,mat_array,i_mat,ierr)
4173: .ve
4175: See the Fortran chapter of the users manual and
4176: petsc/src/mat/examples/tests for details
4178: Level: advanced
4180: .seealso: MatGetArray(), MatRestoreArrayF90()
4181: @*/
4182: PetscErrorCode MatRestoreArray(Mat mat,PetscScalar *v[])
4183: {
4189: MatPreallocated(mat);
4191: #if defined(PETSC_USE_BOPT_g)
4192: CHKMEMQ;
4193: #endif
4194: if (!mat->ops->restorearray) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
4195: (*mat->ops->restorearray)(mat,v);
4196: PetscObjectIncreaseState((PetscObject)mat);
4197: return(0);
4198: }
4202: /*@C
4203: MatGetSubMatrices - Extracts several submatrices from a matrix. If submat
4204: points to an array of valid matrices, they may be reused to store the new
4205: submatrices.
4207: Collective on Mat
4209: Input Parameters:
4210: + mat - the matrix
4211: . n - the number of submatrixes to be extracted (on this processor, may be zero)
4212: . irow, icol - index sets of rows and columns to extract
4213: - scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
4215: Output Parameter:
4216: . submat - the array of submatrices
4218: Notes:
4219: MatGetSubMatrices() can extract only sequential submatrices
4220: (from both sequential and parallel matrices). Use MatGetSubMatrix()
4221: to extract a parallel submatrix.
4223: When extracting submatrices from a parallel matrix, each processor can
4224: form a different submatrix by setting the rows and columns of its
4225: individual index sets according to the local submatrix desired.
4227: When finished using the submatrices, the user should destroy
4228: them with MatDestroyMatrices().
4230: MAT_REUSE_MATRIX can only be used when the nonzero structure of the
4231: original matrix has not changed from that last call to MatGetSubMatrices().
4233: This routine creates the matrices in submat; you should NOT create them before
4234: calling it. It also allocates the array of matrix pointers submat.
4236: Fortran Note:
4237: The Fortran interface is slightly different from that given below; it
4238: requires one to pass in as submat a Mat (integer) array of size at least m.
4240: Level: advanced
4242: Concepts: matrices^accessing submatrices
4243: Concepts: submatrices
4245: .seealso: MatDestroyMatrices(), MatGetSubMatrix(), MatGetRow(), MatGetDiagonal()
4246: @*/
4247: PetscErrorCode MatGetSubMatrices(Mat mat,PetscInt n,const IS irow[],const IS icol[],MatReuse scall,Mat *submat[])
4248: {
4250: PetscInt i;
4251: PetscTruth eq;
4256: MatPreallocated(mat);
4257: if (n) {
4262: }
4264: if (n && scall == MAT_REUSE_MATRIX) {
4267: }
4268: if (!mat->ops->getsubmatrices) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
4269: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4270: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4272: PetscLogEventBegin(MAT_GetSubMatrices,mat,0,0,0);
4273: (*mat->ops->getsubmatrices)(mat,n,irow,icol,scall,submat);
4274: PetscLogEventEnd(MAT_GetSubMatrices,mat,0,0,0);
4275: for (i=0; i<n; i++) {
4276: if (mat->symmetric || mat->structurally_symmetric || mat->hermitian) {
4277: ISEqual(irow[i],icol[i],&eq);
4278: if (eq) {
4279: if (mat->symmetric){
4280: MatSetOption((*submat)[i],MAT_SYMMETRIC);
4281: } else if (mat->hermitian) {
4282: MatSetOption((*submat)[i],MAT_HERMITIAN);
4283: } else if (mat->structurally_symmetric) {
4284: MatSetOption((*submat)[i],MAT_STRUCTURALLY_SYMMETRIC);
4285: }
4286: }
4287: }
4288: }
4289: return(0);
4290: }
4294: /*@C
4295: MatDestroyMatrices - Destroys a set of matrices obtained with MatGetSubMatrices().
4297: Collective on Mat
4299: Input Parameters:
4300: + n - the number of local matrices
4301: - mat - the matrices (note that this is a pointer to the array of matrices, just to match the calling
4302: sequence of MatGetSubMatrices())
4304: Level: advanced
4306: Notes: Frees not only the matrices, but also the array that contains the matrices
4308: .seealso: MatGetSubMatrices()
4309: @*/
4310: PetscErrorCode MatDestroyMatrices(PetscInt n,Mat *mat[])
4311: {
4313: PetscInt i;
4316: if (n < 0) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Trying to destroy negative number of matrices %D",n);
4318: for (i=0; i<n; i++) {
4319: MatDestroy((*mat)[i]);
4320: }
4321: /* memory is allocated even if n = 0 */
4322: PetscFree(*mat);
4323: return(0);
4324: }
4328: /*@
4329: MatIncreaseOverlap - Given a set of submatrices indicated by index sets,
4330: replaces the index sets by larger ones that represent submatrices with
4331: additional overlap.
4333: Collective on Mat
4335: Input Parameters:
4336: + mat - the matrix
4337: . n - the number of index sets
4338: . is - the array of index sets (these index sets will changed during the call)
4339: - ov - the additional overlap requested
4341: Level: developer
4343: Concepts: overlap
4344: Concepts: ASM^computing overlap
4346: .seealso: MatGetSubMatrices()
4347: @*/
4348: PetscErrorCode MatIncreaseOverlap(Mat mat,PetscInt n,IS is[],PetscInt ov)
4349: {
4355: MatPreallocated(mat);
4356: if (n < 0) SETERRQ1(PETSC_ERR_ARG_OUTOFRANGE,"Must have one or more domains, you have %D",n);
4357: if (n) {
4360: }
4361: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4362: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4364: if (!ov) return(0);
4365: if (!mat->ops->increaseoverlap) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
4366: PetscLogEventBegin(MAT_IncreaseOverlap,mat,0,0,0);
4367: (*mat->ops->increaseoverlap)(mat,n,is,ov);
4368: PetscLogEventEnd(MAT_IncreaseOverlap,mat,0,0,0);
4369: return(0);
4370: }
4374: /*@
4375: MatPrintHelp - Prints all the options for the matrix.
4377: Collective on Mat
4379: Input Parameter:
4380: . mat - the matrix
4382: Options Database Keys:
4383: + -help - Prints matrix options
4384: - -h - Prints matrix options
4386: Level: developer
4388: .seealso: MatCreate(), MatCreateXXX()
4389: @*/
4390: PetscErrorCode MatPrintHelp(Mat mat)
4391: {
4392: static PetscTruth called = PETSC_FALSE;
4393: PetscErrorCode ierr;
4398: MatPreallocated(mat);
4400: if (!called) {
4401: if (mat->ops->printhelp) {
4402: (*mat->ops->printhelp)(mat);
4403: }
4404: called = PETSC_TRUE;
4405: }
4406: return(0);
4407: }
4411: /*@
4412: MatGetBlockSize - Returns the matrix block size; useful especially for the
4413: block row and block diagonal formats.
4414:
4415: Not Collective
4417: Input Parameter:
4418: . mat - the matrix
4420: Output Parameter:
4421: . bs - block size
4423: Notes:
4424: Block diagonal formats are MATSEQBDIAG, MATMPIBDIAG.
4425: Block row formats are MATSEQBAIJ, MATMPIBAIJ, MATSEQSBAIJ, MATMPISBAIJ
4427: Level: intermediate
4429: Concepts: matrices^block size
4431: .seealso: MatCreateSeqBAIJ(), MatCreateMPIBAIJ(), MatCreateSeqBDiag(), MatCreateMPIBDiag()
4432: @*/
4433: PetscErrorCode MatGetBlockSize(Mat mat,PetscInt *bs)
4434: {
4438: MatPreallocated(mat);
4440: *bs = mat->bs;
4441: return(0);
4442: }
4446: /*@
4447: MatSetBlockSize - Sets the matrix block size; for many matrix types you
4448: cannot use this and MUST set the blocksize when you preallocate the matrix
4449:
4450: Not Collective
4452: Input Parameters:
4453: + mat - the matrix
4454: - bs - block size
4456: Notes:
4457: Only works for shell and AIJ matrices
4459: Level: intermediate
4461: Concepts: matrices^block size
4463: .seealso: MatCreateSeqBAIJ(), MatCreateMPIBAIJ(), MatCreateSeqBDiag(), MatCreateMPIBDiag(), MatGetBlockSize()
4464: @*/
4465: PetscErrorCode MatSetBlockSize(Mat mat,PetscInt bs)
4466: {
4472: MatPreallocated(mat);
4473: if (mat->ops->setblocksize) {
4474: mat->bs = bs;
4475: (*mat->ops->setblocksize)(mat,bs);
4476: } else {
4477: SETERRQ1(PETSC_ERR_ARG_INCOMP,"Cannot set the blocksize for matrix type %s",mat->type_name);
4478: }
4479: return(0);
4480: }
4484: /*@C
4485: MatGetRowIJ - Returns the compressed row storage i and j indices for sequential matrices.
4487: Collective on Mat
4489: Input Parameters:
4490: + mat - the matrix
4491: . shift - 0 or 1 indicating we want the indices starting at 0 or 1
4492: - symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
4493: symmetrized
4495: Output Parameters:
4496: + n - number of rows in the (possibly compressed) matrix
4497: . ia - the row pointers
4498: . ja - the column indices
4499: - done - PETSC_TRUE or PETSC_FALSE, indicating whether the values have been returned
4501: Level: developer
4503: .seealso: MatGetColumnIJ(), MatRestoreRowIJ()
4504: @*/
4505: PetscErrorCode MatGetRowIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
4506: {
4512: MatPreallocated(mat);
4517: if (!mat->ops->getrowij) *done = PETSC_FALSE;
4518: else {
4519: *done = PETSC_TRUE;
4520: (*mat->ops->getrowij)(mat,shift,symmetric,n,ia,ja,done);
4521: }
4522: return(0);
4523: }
4527: /*@C
4528: MatGetColumnIJ - Returns the compressed column storage i and j indices for sequential matrices.
4530: Collective on Mat
4532: Input Parameters:
4533: + mat - the matrix
4534: . shift - 1 or zero indicating we want the indices starting at 0 or 1
4535: - symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
4536: symmetrized
4538: Output Parameters:
4539: + n - number of columns in the (possibly compressed) matrix
4540: . ia - the column pointers
4541: . ja - the row indices
4542: - done - PETSC_TRUE or PETSC_FALSE, indicating whether the values have been returned
4544: Level: developer
4546: .seealso: MatGetRowIJ(), MatRestoreColumnIJ()
4547: @*/
4548: PetscErrorCode MatGetColumnIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
4549: {
4555: MatPreallocated(mat);
4561: if (!mat->ops->getcolumnij) *done = PETSC_FALSE;
4562: else {
4563: *done = PETSC_TRUE;
4564: (*mat->ops->getcolumnij)(mat,shift,symmetric,n,ia,ja,done);
4565: }
4566: return(0);
4567: }
4571: /*@C
4572: MatRestoreRowIJ - Call after you are completed with the ia,ja indices obtained with
4573: MatGetRowIJ().
4575: Collective on Mat
4577: Input Parameters:
4578: + mat - the matrix
4579: . shift - 1 or zero indicating we want the indices starting at 0 or 1
4580: - symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
4581: symmetrized
4583: Output Parameters:
4584: + n - size of (possibly compressed) matrix
4585: . ia - the row pointers
4586: . ja - the column indices
4587: - done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
4589: Level: developer
4591: .seealso: MatGetRowIJ(), MatRestoreColumnIJ()
4592: @*/
4593: PetscErrorCode MatRestoreRowIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
4594: {
4600: MatPreallocated(mat);
4605: if (!mat->ops->restorerowij) *done = PETSC_FALSE;
4606: else {
4607: *done = PETSC_TRUE;
4608: (*mat->ops->restorerowij)(mat,shift,symmetric,n,ia,ja,done);
4609: }
4610: return(0);
4611: }
4615: /*@C
4616: MatRestoreColumnIJ - Call after you are completed with the ia,ja indices obtained with
4617: MatGetColumnIJ().
4619: Collective on Mat
4621: Input Parameters:
4622: + mat - the matrix
4623: . shift - 1 or zero indicating we want the indices starting at 0 or 1
4624: - symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
4625: symmetrized
4627: Output Parameters:
4628: + n - size of (possibly compressed) matrix
4629: . ia - the column pointers
4630: . ja - the row indices
4631: - done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
4633: Level: developer
4635: .seealso: MatGetColumnIJ(), MatRestoreRowIJ()
4636: @*/
4637: PetscErrorCode MatRestoreColumnIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
4638: {
4644: MatPreallocated(mat);
4649: if (!mat->ops->restorecolumnij) *done = PETSC_FALSE;
4650: else {
4651: *done = PETSC_TRUE;
4652: (*mat->ops->restorecolumnij)(mat,shift,symmetric,n,ia,ja,done);
4653: }
4654: return(0);
4655: }
4659: /*@C
4660: MatColoringPatch -Used inside matrix coloring routines that
4661: use MatGetRowIJ() and/or MatGetColumnIJ().
4663: Collective on Mat
4665: Input Parameters:
4666: + mat - the matrix
4667: . n - number of colors
4668: - colorarray - array indicating color for each column
4670: Output Parameters:
4671: . iscoloring - coloring generated using colorarray information
4673: Level: developer
4675: .seealso: MatGetRowIJ(), MatGetColumnIJ()
4677: @*/
4678: PetscErrorCode MatColoringPatch(Mat mat,PetscInt n,PetscInt ncolors,ISColoringValue colorarray[],ISColoring *iscoloring)
4679: {
4685: MatPreallocated(mat);
4689: if (!mat->ops->coloringpatch){
4690: ISColoringCreate(mat->comm,n,colorarray,iscoloring);
4691: } else {
4692: (*mat->ops->coloringpatch)(mat,n,ncolors,colorarray,iscoloring);
4693: }
4694: return(0);
4695: }
4700: /*@
4701: MatSetUnfactored - Resets a factored matrix to be treated as unfactored.
4703: Collective on Mat
4705: Input Parameter:
4706: . mat - the factored matrix to be reset
4708: Notes:
4709: This routine should be used only with factored matrices formed by in-place
4710: factorization via ILU(0) (or by in-place LU factorization for the MATSEQDENSE
4711: format). This option can save memory, for example, when solving nonlinear
4712: systems with a matrix-free Newton-Krylov method and a matrix-based, in-place
4713: ILU(0) preconditioner.
4715: Note that one can specify in-place ILU(0) factorization by calling
4716: .vb
4717: PCType(pc,PCILU);
4718: PCILUSeUseInPlace(pc);
4719: .ve
4720: or by using the options -pc_type ilu -pc_ilu_in_place
4722: In-place factorization ILU(0) can also be used as a local
4723: solver for the blocks within the block Jacobi or additive Schwarz
4724: methods (runtime option: -sub_pc_ilu_in_place). See the discussion
4725: of these preconditioners in the users manual for details on setting
4726: local solver options.
4728: Most users should employ the simplified KSP interface for linear solvers
4729: instead of working directly with matrix algebra routines such as this.
4730: See, e.g., KSPCreate().
4732: Level: developer
4734: .seealso: PCILUSetUseInPlace(), PCLUSetUseInPlace()
4736: Concepts: matrices^unfactored
4738: @*/
4739: PetscErrorCode MatSetUnfactored(Mat mat)
4740: {
4746: MatPreallocated(mat);
4747: mat->factor = 0;
4748: if (!mat->ops->setunfactored) return(0);
4749: (*mat->ops->setunfactored)(mat);
4750: return(0);
4751: }
4753: /*MC
4754: MatGetArrayF90 - Accesses a matrix array from Fortran90.
4756: Synopsis:
4757: MatGetArrayF90(Mat x,{Scalar, pointer :: xx_v(:)},integer ierr)
4759: Not collective
4761: Input Parameter:
4762: . x - matrix
4764: Output Parameters:
4765: + xx_v - the Fortran90 pointer to the array
4766: - ierr - error code
4768: Example of Usage:
4769: .vb
4770: PetscScalar, pointer xx_v(:)
4771: ....
4772: call MatGetArrayF90(x,xx_v,ierr)
4773: a = xx_v(3)
4774: call MatRestoreArrayF90(x,xx_v,ierr)
4775: .ve
4777: Notes:
4778: Not yet supported for all F90 compilers
4780: Level: advanced
4782: .seealso: MatRestoreArrayF90(), MatGetArray(), MatRestoreArray()
4784: Concepts: matrices^accessing array
4786: M*/
4788: /*MC
4789: MatRestoreArrayF90 - Restores a matrix array that has been
4790: accessed with MatGetArrayF90().
4792: Synopsis:
4793: MatRestoreArrayF90(Mat x,{Scalar, pointer :: xx_v(:)},integer ierr)
4795: Not collective
4797: Input Parameters:
4798: + x - matrix
4799: - xx_v - the Fortran90 pointer to the array
4801: Output Parameter:
4802: . ierr - error code
4804: Example of Usage:
4805: .vb
4806: PetscScalar, pointer xx_v(:)
4807: ....
4808: call MatGetArrayF90(x,xx_v,ierr)
4809: a = xx_v(3)
4810: call MatRestoreArrayF90(x,xx_v,ierr)
4811: .ve
4812:
4813: Notes:
4814: Not yet supported for all F90 compilers
4816: Level: advanced
4818: .seealso: MatGetArrayF90(), MatGetArray(), MatRestoreArray()
4820: M*/
4825: /*@
4826: MatGetSubMatrix - Gets a single submatrix on the same number of processors
4827: as the original matrix.
4829: Collective on Mat
4831: Input Parameters:
4832: + mat - the original matrix
4833: . isrow - rows this processor should obtain
4834: . iscol - columns for all processors you wish to keep
4835: . csize - number of columns "local" to this processor (does nothing for sequential
4836: matrices). This should match the result from VecGetLocalSize(x,...) if you
4837: plan to use the matrix in a A*x; alternatively, you can use PETSC_DECIDE
4838: - cll - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
4840: Output Parameter:
4841: . newmat - the new submatrix, of the same type as the old
4843: Level: advanced
4845: Notes: the iscol argument MUST be the same on each processor. You might be
4846: able to create the iscol argument with ISAllGather().
4848: The first time this is called you should use a cll of MAT_INITIAL_MATRIX,
4849: the MatGetSubMatrix() routine will create the newmat for you. Any additional calls
4850: to this routine with a mat of the same nonzero structure and with a cll of MAT_REUSE_MATRIX
4851: will reuse the matrix generated the first time.
4853: Concepts: matrices^submatrices
4855: .seealso: MatGetSubMatrices(), ISAllGather()
4856: @*/
4857: PetscErrorCode MatGetSubMatrix(Mat mat,IS isrow,IS iscol,PetscInt csize,MatReuse cll,Mat *newmat)
4858: {
4860: PetscMPIInt size;
4861: Mat *local;
4870: MatPreallocated(mat);
4871: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4872: MPI_Comm_size(mat->comm,&size);
4874: /* if original matrix is on just one processor then use submatrix generated */
4875: if (!mat->ops->getsubmatrix && size == 1 && cll == MAT_REUSE_MATRIX) {
4876: MatGetSubMatrices(mat,1,&isrow,&iscol,MAT_REUSE_MATRIX,&newmat);
4877: return(0);
4878: } else if (!mat->ops->getsubmatrix && size == 1) {
4879: MatGetSubMatrices(mat,1,&isrow,&iscol,MAT_INITIAL_MATRIX,&local);
4880: *newmat = *local;
4881: PetscFree(local);
4882: return(0);
4883: }
4885: if (!mat->ops->getsubmatrix) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
4886: (*mat->ops->getsubmatrix)(mat,isrow,iscol,csize,cll,newmat);
4887: PetscObjectIncreaseState((PetscObject)*newmat);
4888: return(0);
4889: }
4893: /*@C
4894: MatGetPetscMaps - Returns the maps associated with the matrix.
4896: Not Collective
4898: Input Parameter:
4899: . mat - the matrix
4901: Output Parameters:
4902: + rmap - the row (right) map
4903: - cmap - the column (left) map
4905: Level: developer
4907: Concepts: maps^getting from matrix
4909: @*/
4910: PetscErrorCode MatGetPetscMaps(Mat mat,PetscMap *rmap,PetscMap *cmap)
4911: {
4917: MatPreallocated(mat);
4918: (*mat->ops->getmaps)(mat,rmap,cmap);
4919: return(0);
4920: }
4922: /*
4923: Version that works for all PETSc matrices
4924: */
4927: PetscErrorCode MatGetPetscMaps_Petsc(Mat mat,PetscMap *rmap,PetscMap *cmap)
4928: {
4930: if (rmap) *rmap = mat->rmap;
4931: if (cmap) *cmap = mat->cmap;
4932: return(0);
4933: }
4937: /*@
4938: MatStashSetInitialSize - sets the sizes of the matrix stash, that is
4939: used during the assembly process to store values that belong to
4940: other processors.
4942: Not Collective
4944: Input Parameters:
4945: + mat - the matrix
4946: . size - the initial size of the stash.
4947: - bsize - the initial size of the block-stash(if used).
4949: Options Database Keys:
4950: + -matstash_initial_size <size> or <size0,size1,...sizep-1>
4951: - -matstash_block_initial_size <bsize> or <bsize0,bsize1,...bsizep-1>
4953: Level: intermediate
4955: Notes:
4956: The block-stash is used for values set with VecSetValuesBlocked() while
4957: the stash is used for values set with VecSetValues()
4959: Run with the option -log_info and look for output of the form
4960: MatAssemblyBegin_MPIXXX:Stash has MM entries, uses nn mallocs.
4961: to determine the appropriate value, MM, to use for size and
4962: MatAssemblyBegin_MPIXXX:Block-Stash has BMM entries, uses nn mallocs.
4963: to determine the value, BMM to use for bsize
4965: Concepts: stash^setting matrix size
4966: Concepts: matrices^stash
4968: @*/
4969: PetscErrorCode MatStashSetInitialSize(Mat mat,PetscInt size, PetscInt bsize)
4970: {
4976: MatPreallocated(mat);
4977: MatStashSetInitialSize_Private(&mat->stash,size);
4978: MatStashSetInitialSize_Private(&mat->bstash,bsize);
4979: return(0);
4980: }
4984: /*@
4985: MatInterpolateAdd - w = y + A*x or A'*x depending on the shape of
4986: the matrix
4988: Collective on Mat
4990: Input Parameters:
4991: + mat - the matrix
4992: . x,y - the vectors
4993: - w - where the result is stored
4995: Level: intermediate
4997: Notes:
4998: w may be the same vector as y.
5000: This allows one to use either the restriction or interpolation (its transpose)
5001: matrix to do the interpolation
5003: Concepts: interpolation
5005: .seealso: MatMultAdd(), MatMultTransposeAdd(), MatRestrict()
5007: @*/
5008: PetscErrorCode MatInterpolateAdd(Mat A,Vec x,Vec y,Vec w)
5009: {
5011: PetscInt M,N;
5019: MatPreallocated(A);
5020: MatGetSize(A,&M,&N);
5021: if (N > M) {
5022: MatMultTransposeAdd(A,x,y,w);
5023: } else {
5024: MatMultAdd(A,x,y,w);
5025: }
5026: return(0);
5027: }
5031: /*@
5032: MatInterpolate - y = A*x or A'*x depending on the shape of
5033: the matrix
5035: Collective on Mat
5037: Input Parameters:
5038: + mat - the matrix
5039: - x,y - the vectors
5041: Level: intermediate
5043: Notes:
5044: This allows one to use either the restriction or interpolation (its transpose)
5045: matrix to do the interpolation
5047: Concepts: matrices^interpolation
5049: .seealso: MatMultAdd(), MatMultTransposeAdd(), MatRestrict()
5051: @*/
5052: PetscErrorCode MatInterpolate(Mat A,Vec x,Vec y)
5053: {
5055: PetscInt M,N;
5062: MatPreallocated(A);
5063: MatGetSize(A,&M,&N);
5064: if (N > M) {
5065: MatMultTranspose(A,x,y);
5066: } else {
5067: MatMult(A,x,y);
5068: }
5069: return(0);
5070: }
5074: /*@
5075: MatRestrict - y = A*x or A'*x
5077: Collective on Mat
5079: Input Parameters:
5080: + mat - the matrix
5081: - x,y - the vectors
5083: Level: intermediate
5085: Notes:
5086: This allows one to use either the restriction or interpolation (its transpose)
5087: matrix to do the restriction
5089: Concepts: matrices^restriction
5091: .seealso: MatMultAdd(), MatMultTransposeAdd(), MatInterpolate()
5093: @*/
5094: PetscErrorCode MatRestrict(Mat A,Vec x,Vec y)
5095: {
5097: PetscInt M,N;
5104: MatPreallocated(A);
5105: MatGetSize(A,&M,&N);
5106: if (N > M) {
5107: MatMult(A,x,y);
5108: } else {
5109: MatMultTranspose(A,x,y);
5110: }
5111: return(0);
5112: }
5116: /*@C
5117: MatNullSpaceAttach - attaches a null space to a matrix.
5118: This null space will be removed from the resulting vector whenever
5119: MatMult() is called
5121: Collective on Mat
5123: Input Parameters:
5124: + mat - the matrix
5125: - nullsp - the null space object
5127: Level: developer
5129: Notes:
5130: Overwrites any previous null space that may have been attached
5132: Concepts: null space^attaching to matrix
5134: .seealso: MatCreate(), MatNullSpaceCreate()
5135: @*/
5136: PetscErrorCode MatNullSpaceAttach(Mat mat,MatNullSpace nullsp)
5137: {
5143: MatPreallocated(mat);
5146: if (mat->nullsp) {
5147: MatNullSpaceDestroy(mat->nullsp);
5148: }
5149: mat->nullsp = nullsp;
5150: PetscObjectReference((PetscObject)nullsp);
5151: return(0);
5152: }
5156: /*@
5157: MatICCFactor - Performs in-place incomplete Cholesky factorization of matrix.
5159: Collective on Mat
5161: Input Parameters:
5162: + mat - the matrix
5163: . row - row/column permutation
5164: . fill - expected fill factor >= 1.0
5165: - level - level of fill, for ICC(k)
5167: Notes:
5168: Probably really in-place only when level of fill is zero, otherwise allocates
5169: new space to store factored matrix and deletes previous memory.
5171: Most users should employ the simplified KSP interface for linear solvers
5172: instead of working directly with matrix algebra routines such as this.
5173: See, e.g., KSPCreate().
5175: Level: developer
5177: Concepts: matrices^incomplete Cholesky factorization
5178: Concepts: Cholesky factorization
5180: .seealso: MatICCFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
5181: @*/
5182: PetscErrorCode MatICCFactor(Mat mat,IS row,MatFactorInfo* info)
5183: {
5189: MatPreallocated(mat);
5192: if (mat->M != mat->N) SETERRQ(PETSC_ERR_ARG_WRONG,"matrix must be square");
5193: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5194: if (mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5195: if (!mat->ops->iccfactor) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
5196: (*mat->ops->iccfactor)(mat,row,info);
5197: PetscObjectIncreaseState((PetscObject)mat);
5198: return(0);
5199: }
5203: /*@
5204: MatSetValuesAdic - Sets values computed with ADIC automatic differentiation into a matrix.
5206: Not Collective
5208: Input Parameters:
5209: + mat - the matrix
5210: - v - the values compute with ADIC
5212: Level: developer
5214: Notes:
5215: Must call MatSetColoring() before using this routine. Also this matrix must already
5216: have its nonzero pattern determined.
5218: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
5219: MatSetValues(), MatSetColoring(), MatSetValuesAdifor()
5220: @*/
5221: PetscErrorCode MatSetValuesAdic(Mat mat,void *v)
5222: {
5230: if (!mat->assembled) {
5231: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
5232: }
5233: PetscLogEventBegin(MAT_SetValues,mat,0,0,0);
5234: if (!mat->ops->setvaluesadic) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
5235: (*mat->ops->setvaluesadic)(mat,v);
5236: PetscLogEventEnd(MAT_SetValues,mat,0,0,0);
5237: MatView_Private(mat);
5238: PetscObjectIncreaseState((PetscObject)mat);
5239: return(0);
5240: }
5245: /*@
5246: MatSetColoring - Sets a coloring used by calls to MatSetValuesAdic()
5248: Not Collective
5250: Input Parameters:
5251: + mat - the matrix
5252: - coloring - the coloring
5254: Level: developer
5256: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
5257: MatSetValues(), MatSetValuesAdic()
5258: @*/
5259: PetscErrorCode MatSetColoring(Mat mat,ISColoring coloring)
5260: {
5268: if (!mat->assembled) {
5269: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
5270: }
5271: if (!mat->ops->setcoloring) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
5272: (*mat->ops->setcoloring)(mat,coloring);
5273: return(0);
5274: }
5278: /*@
5279: MatSetValuesAdifor - Sets values computed with automatic differentiation into a matrix.
5281: Not Collective
5283: Input Parameters:
5284: + mat - the matrix
5285: . nl - leading dimension of v
5286: - v - the values compute with ADIFOR
5288: Level: developer
5290: Notes:
5291: Must call MatSetColoring() before using this routine. Also this matrix must already
5292: have its nonzero pattern determined.
5294: .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
5295: MatSetValues(), MatSetColoring()
5296: @*/
5297: PetscErrorCode MatSetValuesAdifor(Mat mat,PetscInt nl,void *v)
5298: {
5306: if (!mat->assembled) {
5307: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
5308: }
5309: PetscLogEventBegin(MAT_SetValues,mat,0,0,0);
5310: if (!mat->ops->setvaluesadifor) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
5311: (*mat->ops->setvaluesadifor)(mat,nl,v);
5312: PetscLogEventEnd(MAT_SetValues,mat,0,0,0);
5313: PetscObjectIncreaseState((PetscObject)mat);
5314: return(0);
5315: }
5317: EXTERN PetscErrorCode MatMPIAIJDiagonalScaleLocal(Mat,Vec);
5318: EXTERN PetscErrorCode MatMPIBAIJDiagonalScaleLocal(Mat,Vec);
5322: /*@
5323: MatDiagonalScaleLocal - Scales columns of a matrix given the scaling values including the
5324: ghosted ones.
5326: Not Collective
5328: Input Parameters:
5329: + mat - the matrix
5330: - diag = the diagonal values, including ghost ones
5332: Level: developer
5334: Notes: Works only for MPIAIJ and MPIBAIJ matrices
5335:
5336: .seealso: MatDiagonalScale()
5337: @*/
5338: PetscErrorCode MatDiagonalScaleLocal(Mat mat,Vec diag)
5339: {
5341: PetscMPIInt size;
5348: if (!mat->assembled) {
5349: SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
5350: }
5351: PetscLogEventBegin(MAT_Scale,mat,0,0,0);
5352: MPI_Comm_size(mat->comm,&size);
5353: if (size == 1) {
5354: PetscInt n,m;
5355: VecGetSize(diag,&n);
5356: MatGetSize(mat,0,&m);
5357: if (m == n) {
5358: MatDiagonalScale(mat,0,diag);
5359: } else {
5360: SETERRQ(PETSC_ERR_SUP,"Only supported for sequential matrices when no ghost points/periodic conditions");
5361: }
5362: } else {
5363: PetscErrorCode (*f)(Mat,Vec);
5364: PetscObjectQueryFunction((PetscObject)mat,"MatDiagonalScaleLocal_C",(void (**)(void))&f);
5365: if (f) {
5366: (*f)(mat,diag);
5367: } else {
5368: SETERRQ(PETSC_ERR_SUP,"Only supported for MPIAIJ and MPIBAIJ parallel matrices");
5369: }
5370: }
5371: PetscLogEventEnd(MAT_Scale,mat,0,0,0);
5372: PetscObjectIncreaseState((PetscObject)mat);
5373: return(0);
5374: }
5378: /*@
5379: MatGetInertia - Gets the inertia from a factored matrix
5381: Collective on Mat
5383: Input Parameter:
5384: . mat - the matrix
5386: Output Parameters:
5387: + nneg - number of negative eigenvalues
5388: . nzero - number of zero eigenvalues
5389: - npos - number of positive eigenvalues
5391: Level: advanced
5393: Notes: Matrix must have been factored by MatCholeskyFactor()
5396: @*/
5397: PetscErrorCode MatGetInertia(Mat mat,PetscInt *nneg,PetscInt *nzero,PetscInt *npos)
5398: {
5404: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
5405: if (!mat->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Numeric factor mat is not assembled");
5406: if (!mat->ops->getinertia) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
5407: (*mat->ops->getinertia)(mat,nneg,nzero,npos);
5408: return(0);
5409: }
5411: /* ----------------------------------------------------------------*/
5414: /*@
5415: MatSolves - Solves A x = b, given a factored matrix, for a collection of vectors
5417: Collective on Mat and Vecs
5419: Input Parameters:
5420: + mat - the factored matrix
5421: - b - the right-hand-side vectors
5423: Output Parameter:
5424: . x - the result vectors
5426: Notes:
5427: The vectors b and x cannot be the same. I.e., one cannot
5428: call MatSolves(A,x,x).
5430: Notes:
5431: Most users should employ the simplified KSP interface for linear solvers
5432: instead of working directly with matrix algebra routines such as this.
5433: See, e.g., KSPCreate().
5435: Level: developer
5437: Concepts: matrices^triangular solves
5439: .seealso: MatSolveAdd(), MatSolveTranspose(), MatSolveTransposeAdd(), MatSolve()
5440: @*/
5441: PetscErrorCode MatSolves(Mat mat,Vecs b,Vecs x)
5442: {
5448: MatPreallocated(mat);
5449: if (x == b) SETERRQ(PETSC_ERR_ARG_IDN,"x and b must be different vectors");
5450: if (!mat->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
5451: if (!mat->M && !mat->N) return(0);
5453: if (!mat->ops->solves) SETERRQ1(PETSC_ERR_SUP,"Mat type %s",mat->type_name);
5454: PetscLogEventBegin(MAT_Solves,mat,0,0,0);
5455: (*mat->ops->solves)(mat,b,x);
5456: PetscLogEventEnd(MAT_Solves,mat,0,0,0);
5457: return(0);
5458: }
5462: /*@C
5463: MatIsSymmetric - Test whether a matrix is symmetric
5465: Collective on Mat
5467: Input Parameter:
5468: + A - the matrix to test
5469: - tol - difference between value and its transpose less than this amount counts as equal (use 0.0 for exact transpose)
5471: Output Parameters:
5472: . flg - the result
5474: Level: intermediate
5476: Concepts: matrix^symmetry
5478: .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetricKnown()
5479: @*/
5480: PetscErrorCode MatIsSymmetric(Mat A,PetscReal tol,PetscTruth *flg)
5481: {
5487: if (!A->symmetric_set) {
5488: if (!A->ops->issymmetric) {
5489: MatType mattype;
5490: MatGetType(A,&mattype);
5491: SETERRQ1(PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for symmetric",mattype);
5492: }
5493: (*A->ops->issymmetric)(A,tol,&A->symmetric);
5494: A->symmetric_set = PETSC_TRUE;
5495: if (A->symmetric) {
5496: A->structurally_symmetric_set = PETSC_TRUE;
5497: A->structurally_symmetric = PETSC_TRUE;
5498: }
5499: }
5500: *flg = A->symmetric;
5501: return(0);
5502: }
5506: /*@C
5507: MatIsSymmetricKnown - Checks the flag on the matrix to see if it is symmetric.
5509: Collective on Mat
5511: Input Parameter:
5512: . A - the matrix to check
5514: Output Parameters:
5515: + set - if the symmetric flag is set (this tells you if the next flag is valid)
5516: - flg - the result
5518: Level: advanced
5520: Concepts: matrix^symmetry
5522: Note: Does not check the matrix values directly, so this may return unknown (set = PETSC_FALSE). Use MatIsSymmetric()
5523: if you want it explicitly checked
5525: .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetric()
5526: @*/
5527: PetscErrorCode MatIsSymmetricKnown(Mat A,PetscTruth *set,PetscTruth *flg)
5528: {
5533: if (A->symmetric_set) {
5534: *set = PETSC_TRUE;
5535: *flg = A->symmetric;
5536: } else {
5537: *set = PETSC_FALSE;
5538: }
5539: return(0);
5540: }
5544: /*@C
5545: MatIsHermitianKnown - Checks the flag on the matrix to see if it is hermitian.
5547: Collective on Mat
5549: Input Parameter:
5550: . A - the matrix to check
5552: Output Parameters:
5553: + set - if the hermitian flag is set (this tells you if the next flag is valid)
5554: - flg - the result
5556: Level: advanced
5558: Concepts: matrix^symmetry
5560: Note: Does not check the matrix values directly, so this may return unknown (set = PETSC_FALSE). Use MatIsHermitian()
5561: if you want it explicitly checked
5563: .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetric()
5564: @*/
5565: PetscErrorCode MatIsHermitianKnown(Mat A,PetscTruth *set,PetscTruth *flg)
5566: {
5571: if (A->hermitian_set) {
5572: *set = PETSC_TRUE;
5573: *flg = A->hermitian;
5574: } else {
5575: *set = PETSC_FALSE;
5576: }
5577: return(0);
5578: }
5582: /*@C
5583: MatIsStructurallySymmetric - Test whether a matrix is structurally symmetric
5585: Collective on Mat
5587: Input Parameter:
5588: . A - the matrix to test
5590: Output Parameters:
5591: . flg - the result
5593: Level: intermediate
5595: Concepts: matrix^symmetry
5597: .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsSymmetric(), MatSetOption()
5598: @*/
5599: PetscErrorCode MatIsStructurallySymmetric(Mat A,PetscTruth *flg)
5600: {
5606: if (!A->structurally_symmetric_set) {
5607: if (!A->ops->isstructurallysymmetric) SETERRQ(PETSC_ERR_SUP,"Matrix does not support checking for structural symmetric");
5608: (*A->ops->isstructurallysymmetric)(A,&A->structurally_symmetric);
5609: A->structurally_symmetric_set = PETSC_TRUE;
5610: }
5611: *flg = A->structurally_symmetric;
5612: return(0);
5613: }
5617: /*@C
5618: MatIsHermitian - Test whether a matrix is Hermitian, i.e. it is the complex conjugate of its transpose.
5620: Collective on Mat
5622: Input Parameter:
5623: . A - the matrix to test
5625: Output Parameters:
5626: . flg - the result
5628: Level: intermediate
5630: Concepts: matrix^symmetry
5632: .seealso: MatTranspose(), MatIsTranspose(), MatIsSymmetric(), MatIsStructurallySymmetric(), MatSetOption()
5633: @*/
5634: PetscErrorCode MatIsHermitian(Mat A,PetscTruth *flg)
5635: {
5641: if (!A->hermitian_set) {
5642: if (!A->ops->ishermitian) SETERRQ(PETSC_ERR_SUP,"Matrix does not support checking for being Hermitian");
5643: (*A->ops->ishermitian)(A,&A->hermitian);
5644: A->hermitian_set = PETSC_TRUE;
5645: if (A->hermitian) {
5646: A->structurally_symmetric_set = PETSC_TRUE;
5647: A->structurally_symmetric = PETSC_TRUE;
5648: }
5649: }
5650: *flg = A->hermitian;
5651: return(0);
5652: }
5657: /*@
5658: MatStashGetInfo - Gets how many values are currently in the vector stash, i.e. need
5659: to be communicated to other processors during the MatAssemblyBegin/End() process
5661: Not collective
5663: Input Parameter:
5664: . vec - the vector
5666: Output Parameters:
5667: + nstash - the size of the stash
5668: . reallocs - the number of additional mallocs incurred.
5669: . bnstash - the size of the block stash
5670: - breallocs - the number of additional mallocs incurred.in the block stash
5671:
5672: Level: advanced
5674: .seealso: MatAssemblyBegin(), MatAssemblyEnd(), Mat, MatStashSetInitialSize()
5675:
5676: @*/
5677: PetscErrorCode MatStashGetInfo(Mat mat,PetscInt *nstash,PetscInt *reallocs,PetscInt *bnstash,PetscInt *brealloc)
5678: {
5681: MatStashGetInfo_Private(&mat->stash,nstash,reallocs);
5682: MatStashGetInfo_Private(&mat->bstash,nstash,reallocs);
5683: return(0);
5684: }
5688: /*@
5689: MatGetVecs - Get vector(s) compatible with the matrix, i.e. with the same
5690: parallel layout
5691:
5692: Collective on Mat
5694: Input Parameter:
5695: . mat - the matrix
5697: Output Parameter:
5698: + right - (optional) vector that the matrix can be multiplied against
5699: - left - (optional) vector that the matrix vector product can be stored in
5701: Level: advanced
5703: .seealso: MatCreate()
5704: @*/
5705: PetscErrorCode MatGetVecs(Mat mat,Vec *right,Vec *left)
5706: {
5712: MatPreallocated(mat);
5713: if (mat->ops->getvecs) {
5714: (*mat->ops->getvecs)(mat,right,left);
5715: } else {
5716: PetscMPIInt size;
5717: MPI_Comm_size(mat->comm, &size);
5718: if (right) {
5719: VecCreate(mat->comm,right);
5720: VecSetSizes(*right,mat->n,PETSC_DETERMINE);
5721: if (size > 1) {VecSetType(*right,VECMPI);}
5722: else {VecSetType(*right,VECSEQ);}
5723: }
5724: if (left) {
5725: VecCreate(mat->comm,left);
5726: VecSetSizes(*left,mat->m,PETSC_DETERMINE);
5727: if (size > 1) {VecSetType(*left,VECMPI);}
5728: else {VecSetType(*left,VECSEQ);}
5729: }
5730: }
5731: if (right) {VecSetBlockSize(*right,mat->bs);}
5732: if (left) {VecSetBlockSize(*left,mat->bs);}
5733: return(0);
5734: }
5738: /*@C
5739: MatFactorInfoInitialize - Initializes a MatFactorInfo data structure
5740: with default values.
5742: Not Collective
5744: Input Parameters:
5745: . info - the MatFactorInfo data structure
5748: Notes: The solvers are generally used through the KSP and PC objects, for example
5749: PCLU, PCILU, PCCHOLESKY, PCICC
5751: Level: developer
5753: .seealso: MatFactorInfo
5754: @*/
5756: PetscErrorCode MatFactorInfoInitialize(MatFactorInfo *info)
5757: {
5761: PetscMemzero(info,sizeof(MatFactorInfo));
5762: return(0);
5763: }
5767: /*@C
5768: MatPtAP - Creates the matrix projection C = P^T * A * P
5770: Collective on Mat
5772: Input Parameters:
5773: + A - the matrix
5774: . P - the projection matrix
5775: . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
5776: - fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(P))
5778: Output Parameters:
5779: . C - the product matrix
5781: Notes:
5782: C will be created and must be destroyed by the user with MatDestroy().
5784: This routine is currently only implemented for pairs of SeqAIJ matrices and classes
5785: which inherit from SeqAIJ. C will be of type MATSEQAIJ.
5787: Level: intermediate
5789: .seealso: MatPtAPSymbolic(),MatPtAPNumeric(),MatMatMult()
5790: @*/
5791: PetscErrorCode MatPtAP(Mat A,Mat P,MatReuse scall,PetscReal fill,Mat *C)
5792: {
5793: PetscErrorCode ierr, (*fA)(Mat,Mat,MatReuse,PetscReal,Mat *), (*fP)(Mat,Mat,MatReuse,PetscReal,Mat *);
5794: Mat Ptmp;
5795: PetscTruth flg;
5800: MatPreallocated(A);
5801: if (!A->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5802: if (A->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5805: MatPreallocated(P);
5806: if (!P->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5807: if (P->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5809: if (P->M!=A->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->M,A->N);
5810: if (fill <=0.0) SETERRQ1(PETSC_ERR_ARG_SIZ,"fill=%g must be > 0.0",fill);
5812: /* This is a crappy hack */
5813: PetscTypeCompare((PetscObject)P,MATSEQMAIJ,&flg);
5814: if (flg) {
5815: MatConvert(P,MATSEQAIJ,&Ptmp);
5816: P = Ptmp;
5817: }
5819: /* For now, we do not dispatch based on the type of A and P */
5820: /* When implementations like _SeqAIJ_MAIJ exist, attack the multiple dispatch problem. */
5821: fA = A->ops->ptap;
5822: if (!fA) SETERRQ1(PETSC_ERR_SUP,"MatPtAP not supported for A of type %s",A->type_name);
5823: fP = P->ops->ptap;
5824: if (!fP) SETERRQ1(PETSC_ERR_SUP,"MatPtAP not supported for P of type %s",P->type_name);
5825: if (fP!=fA) SETERRQ2(PETSC_ERR_ARG_INCOMP,"MatPtAP requires A, %s, to be compatible with P, %s",A->type_name,P->type_name);
5827: PetscLogEventBegin(MAT_PtAP,A,P,0,0);
5828: (*fA)(A,P,scall,fill,C);
5829: PetscLogEventEnd(MAT_PtAP,A,P,0,0);
5831: if (flg) {
5832: MatDestroy(P);
5833: }
5834: PetscTypeCompare((PetscObject)A,MATSEQAIJ,&flg);
5835: MatSetBlockSize(*C,A->bs);
5836: return(0);
5837: }
5839: /*@C
5840: MatPtAPNumeric - Computes the matrix projection C = P^T * A * P
5842: Collective on Mat
5844: Input Parameters:
5845: + A - the matrix
5846: - P - the projection matrix
5848: Output Parameters:
5849: . C - the product matrix
5851: Notes:
5852: C must have been created by calling MatPtAPSymbolic and must be destroyed by
5853: the user using MatDeatroy().
5855: This routine is currently only implemented for pairs of AIJ matrices and classes
5856: which inherit from AIJ. C will be of type MATAIJ.
5858: Level: intermediate
5860: .seealso: MatPtAP(),MatPtAPSymbolic(),MatMatMultNumeric()
5861: @*/
5864: PetscErrorCode MatPtAPNumeric(Mat A,Mat P,Mat C)
5865: {
5866: PetscErrorCode ierr,(*fA)(Mat,Mat,Mat), (*fP)(Mat,Mat,Mat);
5871: MatPreallocated(A);
5872: if (!A->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5873: if (A->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5876: MatPreallocated(P);
5877: if (!P->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5878: if (P->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5881: MatPreallocated(C);
5882: if (!C->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5883: if (C->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5884: if (P->N!=C->M) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->N,C->M);
5885: if (P->M!=A->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->M,A->N);
5886: if (A->M!=A->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->M,A->N);
5887: if (P->N!=C->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->N,C->N);
5889: /* For now, we do not dispatch based on the type of A and P */
5890: /* When implementations like _SeqAIJ_MAIJ exist, attack the multiple dispatch problem. */
5891: fA = A->ops->ptapnumeric;
5892: if (!fA) SETERRQ1(PETSC_ERR_SUP,"MatPtAPNumeric not supported for A of type %s",A->type_name);
5893: fP = P->ops->ptapnumeric;
5894: if (!fP) SETERRQ1(PETSC_ERR_SUP,"MatPtAPNumeric not supported for P of type %s",P->type_name);
5895: if (fP!=fA) SETERRQ2(PETSC_ERR_ARG_INCOMP,"MatPtAPNumeric requires A, %s, to be compatible with P, %s",A->type_name,P->type_name);
5897: PetscLogEventBegin(MAT_PtAPNumeric,A,P,0,0);
5898: (*fA)(A,P,C);
5899: PetscLogEventEnd(MAT_PtAPNumeric,A,P,0,0);
5900: return(0);
5901: }
5903: /*@C
5904: MatPtAPSymbolic - Creates the (i,j) structure of the matrix projection C = P^T * A * P
5906: Collective on Mat
5908: Input Parameters:
5909: + A - the matrix
5910: - P - the projection matrix
5912: Output Parameters:
5913: . C - the (i,j) structure of the product matrix
5915: Notes:
5916: C will be created and must be destroyed by the user with MatDestroy().
5918: This routine is currently only implemented for pairs of SeqAIJ matrices and classes
5919: which inherit from SeqAIJ. C will be of type MATSEQAIJ. The product is computed using
5920: this (i,j) structure by calling MatPtAPNumeric().
5922: Level: intermediate
5924: .seealso: MatPtAP(),MatPtAPNumeric(),MatMatMultSymbolic()
5925: @*/
5928: PetscErrorCode MatPtAPSymbolic(Mat A,Mat P,PetscReal fill,Mat *C)
5929: {
5930: PetscErrorCode ierr, (*fA)(Mat,Mat,PetscReal,Mat*), (*fP)(Mat,Mat,PetscReal,Mat*);
5935: MatPreallocated(A);
5936: if (!A->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5937: if (A->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5940: MatPreallocated(P);
5941: if (!P->assembled) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5942: if (P->factor) SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5945: if (P->M!=A->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->M,A->N);
5946: if (A->M!=A->N) SETERRQ2(PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->M,A->N);
5948: /* For now, we do not dispatch based on the type of A and P */
5949: /* When implementations like _SeqAIJ_MAIJ exist, attack the multiple dispatch problem. */
5950: fA = A->ops->ptapsymbolic;
5951: if (!fA) SETERRQ1(PETSC_ERR_SUP,"MatPtAPSymbolic not supported for A of type %s",A->type_name);
5952: fP = P->ops->ptapsymbolic;
5953: if (!fP) SETERRQ1(PETSC_ERR_SUP,"MatPtAPSymbolic not supported for P of type %s",P->type_name);
5954: if (fP!=fA) SETERRQ2(PETSC_ERR_ARG_INCOMP,"MatPtAPSymbolic requires A, %s, to be compatible with P, %s",A->type_name,P->type_name);
5956: PetscLogEventBegin(MAT_PtAPSymbolic,A,P,0,0);
5957: (*fA)(A,P,fill,C);
5958: PetscLogEventEnd(MAT_PtAPSymbolic,A,P,0,0);
5959: return(0);
5960: }