Вопрос

I'm writing a sparse matrix library in Fortran for fun but came into a little snag. I have a subroutine for matrix multiplication with the interface

subroutine matvec(A,x,y)
    class(sparse_matrix), intent(in) :: A
    real(double_precision), intent(in) :: x(:)
    real(double_precision), intent(inout) :: y(:)
    {etc.}

This uses a sparse matrix type that I've defined myself, the implementation of which is unimportant. Now, I can make things nicer and have a lot less code if A contains an object called iterator:

type :: sparse_matrix
    type(matrix_iterator) :: iterator
    {etc.}

which stores a few variables that keep track of things during matvec. But, if I change the state of iterator and in turn the state of A during matrix multiplication, the compiler will throw a fit because A has intent(in) for that subroutine.

Suppose I change things around and instead define

type :: sparse_matrix
    type(matrix_iterator), pointer :: iterator
    {etc.}

It's no problem if I change the state of iterator during a procedure in which a matrix has intent(in), because the value of the pointer to iterator doesn't change; only the memory stored at that address is affected. This is confirmed by making a reduced test case, which compiles and runs just fine using GCC.

Am I correct in thinking this is an appropriate fix? Or should I change the subroutine so that A has intent(inout)? The fact that it compiled with GCC doesn't necessarily mean it's standard-compliant, nor does it mean it's good programming practice.

To make an analogy with C, suppose I had a function foo(int* const p). If I wrote

*p = 42;

this would be ok, as the value of the pointer doesn't change, only the data stored at the address pointed to. On the other hand, I couldn't write

p = &my_var;

because it's a constant pointer.

Это было полезно?

Решение

Yes, it is OK. Actually this practice is well known and it is used, for example, when doing reference counting memory management, because the right hand side of defined assignment is an intent(in) expression, but you must be able to decrease the reference count in it.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top