Пользовательские операторы в Fortran

У меня возник вопрос о правильном способе программирования пользовательских операторов на Фортране. Чтобы быть более конкретным, я приведу пример моей проблемы. Я работаю над созданием определяемого пользователем типа данных для сферических частиц под названием «Частица». Я хочу определить оператор, который берет существующий массив объектов Particle и добавляет к нему новый объект Particle. Мне было интересно, как я буду определять пользовательские операторы для выполнения такого действия.

В настоящее время у меня есть в определении типа для Particle следующие строки:

procedure, public:: addNewParticleTo
generic:: operator(.spawn.) => addNewParticleTo

После этого у меня есть подпрограмма, которая определяется следующим образом:

subroutine addNewParticleTo(a_LHS, a_RHS)
  implicit none
  class(Particle), dimension(:), allocatable, intent(in):: a_LHS
  class(Particle), dimension(:), allocatable, intent(inout):: a_RHS
  <rest of the code>
end subroutine addNewParticleTo

Я намереваюсь, чтобы оператор вызывался как:

particle .spawn. particleArray

Мне было интересно, правильный ли это способ сделать это. Любые предложения или советы по этому поводу будут очень полезны.


person computanjohn    schedule 18.11.2013    source источник
comment
У меня сложилось впечатление, что operator требует function, а не subroutine.   -  person Kyle Kanos    schedule 18.11.2013
comment
Не могли бы вы предложить, как бы я тогда определил соответствующую функцию для определения такого оператора в целом? Я предполагаю, что я использовал такую ​​конструкцию раньше для перегрузки оператора присваивания для создания конструкторов копирования - и там я использовал подпрограммы.   -  person computanjohn    schedule 18.11.2013
comment
Вы должны иметь возможность сделать это, просто поменяв местами subroutine на function, а затем используя NewparticleArray = particle .spawn. OldparticleArray.   -  person Kyle Kanos    schedule 18.11.2013


Ответы (1)


Чтобы расширить комментарии, вам понадобится код operator как код function. Кроме того, каждый вход должен быть intent(in). Это действительно позволит что-то вроде array = particle .spawn. array.

Однако в вашей подпрограмме требуется еще одно изменение: один из ваших аргументов должен быть скаляром. [Первый, если только вы не играете с атрибутом pass.]

function addNewParticleTo(A, B) result(C)
  class(particle), intent(in) :: A
  class(particle), allocatable, intent(in)  :: B(:)
  class(particle), allocatable :: C(:)
  ! ... code to do the appending
end function

Наконец, мой совет заключается в том, что наличие this в качестве оператора, привязанного к типу, делает вещи довольно сложными, с полиморфизмом и так далее. Кроме того, array = particle .spawn. array кажется очень неинтуитивным.

Вместо этого просто простая подпрограмма, чтобы call add_to_particle_array(all_particles, new_particle) работала, кажется чище. Это ближе к вашему исходному коду, но, увы, не отвечает на ваш вопрос об операторах.

person francescalus    schedule 06.01.2014