Is it fair to say that MatPreallocateInitialize and MatPreallocateSet
need to be in the same scope for this to work?  If so, that will never
work with my code. (Unless I can call repeatedly without having it
reinitialize things.)

I already had everything setup to work with my own bookkeeping (STL
vector and binary_search, in my tests STL set took too much memory).
But I need get the diagonal columns!

So be it.  I'm willing to hack.  May I assume PETSc distributes
columns with the following algorithm:

int diag_cols = total_cols / processors;
if (mpi_rank() < total_cols % processors)
    diag_cols += 1;

Then assume the offsets follow the MPI rank? (i.e. higher rank has
later columns)

Thanks,
-Andrew

On Wed, Jul 2, 2008 at 3:34 PM, Barry Smith <bsmith at mcs.anl.gov> wrote:
>
> On Jul 2, 2008, at 3:25 PM, Andrew Colombi wrote:
>
>> Is MatGetOwnershipRangeColumn a new function?
>
>   Looks like it.
>
>> because I don't think it
>> I have it.  I'm using petsc-2.3.3-p13.  I searched petsc/include for
>> RangeColumn and didn't find anything.
>>
>> I could switch over to MatPreallocateInitialize, but I'm not entirely
>> sure how it works.  The docs reference a chapter in the user manual
>> about performance,
>>
>> "See the chapter in the users manual on performance for more details"
>>
>> But I can't find anything in the PDF manual that mentions
>> PreallocateInitialize or PreallocateSet (I searched the text for that
>> string).
>
>   The manual pages for these macros are pretty extensive; they are not
> discussed in the manual.
>>
>>
>> My first question is, how does MatPreallocateInitialize allocate dnz
>> and onz? It says we should not malloc or free them, but it takes
>> PetscInt *dnz not PetscInt **dnz?  My understanding of how these
>> utilities work is that you do your normal matrix assembly, but use
>> MatPreallocateSet instead of MatSetValues.  Then it just does some
>> counting and when you're done dnz and onz are correct.  Am I correct?
>
>  Yes. See src/dm/da/src/utils/fdda.c for many examples of its use.
>
>   Barry
>
>>
>> Thanks,
>> -Andrew
>>
>> On Wed, Jul 2, 2008 at 1:52 PM, Barry Smith <bsmith at mcs.anl.gov> wrote:
>>>
>>> MatGetOwnershipRangeColumn() will give you the needed information. If you
>>> are coding from C/C++
>>> you might consider using the macro MatPreallocateInitialize() and
>>> friends. These utilities make it
>>> somewhat easier, in some circumstances, to count the entries in the
>>> diagonal and off-diagonal blocks.
>>>
>>>  Barry
>>>
>>> On Jul 2, 2008, at 11:58 AM, Andrew Colombi wrote:
>>>
>>>> Hmm... this has not been my experience.  When A is not square I'm
>>>> finding the that the diagonal portion is also not square.  Instead it
>>>> assigns columns to the diagonal portion by evenly distributing the columns
>>>> among processors.  For example, a 4 by 8 would look like:
>>>>
>>>> (please excuse the embedded HTML, I need it to specify a fixed-width
>>>> font)
>>>>
>>>>    c0  c1  c2  c3  c4  c5  c6  c7
>>>> p0 r0  X   X   X   X
>>>> p0 r1  X   X   X   X
>>>> p1 r2                  X   X   X   X
>>>> p1 r3                  X   X   X   X
>>>>
>>>>
>>>> X marks the diagonal portions for each processor.  I have attempted to
>>>> verify this using the program below.  If you run this code it will complain
>>>> that processor 1 must allocate new memory for "(0, 3)" (which I am
>>>> interpreting to mean the local (0, 3), otherwise known as (2, 3)).  Further
>>>> more you can stop the complaint by incrementing the off-diagonal
>>>> preallocation, and decrementing the diagonal preallocation.  Note, that
>>>> specifying 0 is some special value that isn't 0. If you specify 0 you won't
>>>> get any malloc errors.
>>>>
>>>> Mat A;
>>>> int rows = 4;
>>>> int cols = 8;
>>>>
>>>> if (mpi_rank() == 0)
>>>> {
>>>>  MatCreateMPIAIJ(PETSC_COMM_WORLD, PETSC_DECIDE, PETSC_DECIDE, rows,
>>>> cols,
>>>>                  2, PETSC_NULL, 1, PETSC_NULL, &A);
>>>>  MatSetOption(A, MAT_NEW_NONZERO_ALLOCATION_ERR);
>>>>
>>>>  static const int R = 2;
>>>>  int set_rows[R] = {0, 1};
>>>>  static const int C = 2;
>>>>  int set_cols[C] = {0, 1};
>>>>  double vals[C*R] = {1., 1., 1., 1.};
>>>>  MatSetValues(A, R, set_rows, C, set_cols, vals, ADD_VALUES);
>>>> }
>>>> else
>>>> {
>>>>  MatCreateMPIAIJ(PETSC_COMM_WORLD, PETSC_DECIDE, PETSC_DECIDE,rows,
>>>> cols,
>>>>                  2, PETSC_NULL, 1, PETSC_NULL, &A);
>>>>  MatSetOption(A, MAT_NEW_NONZERO_ALLOCATION_ERR);
>>>>
>>>>  static const int R = 2;
>>>>  int set_rows[R] = {2,3};
>>>>  static const int C = 2;
>>>>  int set_cols[C] = {2,3};
>>>>  double vals[C*R] = {1., 1., 1., 1.};
>>>>  MatSetValues(A, R, set_rows, C, set_cols, vals, ADD_VALUES);
>>>> }
>>>>
>>>> MatAssemblyBegin(A, MAT_FINAL_ASSEMBLY);
>>>> MatAssemblyEnd(A, MAT_FINAL_ASSEMBLY);
>>>>
>>>> On Wed, Jul 2, 2008 at 6:35 AM, Matthew Knepley <knepley at gmail.com>
>>>> wrote:
>>>>>
>>>>> By definition, the diagonal portion is square. Thus you retrieve the
>>>>> local rows [start, end), and then the diagonal block is
>>>>>
>>>>> [start, end) x [start, end)
>>>>>
>>>>> which you can do with
>>>>>
>>>>>
>>>>> http://www-unix.mcs.anl.gov/petsc/petsc-as/snapshots/petsc-current/docs/manualpages/Mat/MatGetOwnershipRange.html
>>>>>
>>>>>  Matt
>>>>>
>>>>> On Wed, Jul 2, 2008 at 2:52 AM, Andrew Colombi <acolombi at gmail.com>
>>>>> wrote:
>>>>>>
>>>>>> I'm letting PETSC_DECIDE how to distribute the rows and columns of my
>>>>>> non-square matrix, and I want to retrieve the columns it's decided to
>>>>>> make the "Diagonal" for a particular process.  How can I do that?  I'm
>>>>>> probably missing something obvious here, but I checked the docs.
>>>>>>
>>>>>> In case some context helps (or inspires a work-around):
>>>>>>
>>>>>> I want this information to count the number of d_nnz and o_nnz to
>>>>>> preallocate perfectly.  This shouldn't be hard to do, but I need to
>>>>>> know the boundary between off-diagonal and diagonal to do it.
>>>>>>
>>>>>> Thanks,
>>>>>> -Andrew
>>>>>>
>>>>>>
>>>>>
>>>>>
>>>>>
>>>>> --
>>>>> What most experimenters take for granted before they begin their
>>>>> experiments is infinitely more interesting than any results to which
>>>>> their experiments lead.
>>>>> -- Norbert Wiener
>>>>>
>>>>>
>>>>
>>>
>>
>
>


Reply via email to