2015-02-20 3 views
2

Я хочу скрыть массив Fortran. Вот как я сейчас делаю это ...Лучший способ маскировать массив Fortran?

where (my_array <=15.0) 
    mask_array = 1 
elsewhere 
    mask_array = 0 
end where 

Так тогда я получаю мой замаскированный массив с:

masked = my_array * mask_array 

Есть более краткий способ сделать это?

ответ

5

Используйте MERGE внутренней функцию:

masked = my_array * merge(1,0,my_array<=15.0) 
+0

Отлично! Это именно то, что я искал. – user14241

+4

На ту же тему 'masked = MERGE (my_array, 0._blah, my_array <= 15)'. – francescalus

3

Или, торчащую с where,

masked = 0 
where (my_array <=15.0) masked = my_array 

Я ожидаю, что существует различие в скорости и потреблении памяти, между использованием where а использование merge, но с верхней части головы я не знаю, что это такое.

2

Здесь есть два разных подхода: один сохраняется where и один использует merge. Во-первых, High Performance Mark упоминает, что могут быть различия в скорости и использовании памяти (подумайте о временных массивах). Я укажу еще одно потенциальное соображение (без принятия оценочного суждения).

subroutine work_with_masked_where(my_array) 
    real, intent(in) :: my_array(:) 
    real, allocatable :: masked(:) 

    allocate(masked(SIZE(my_array)), source=0.) 
    where (my_array <=15.0) masked = my_array 
    ! ... 
end subroutine 

subroutine work_with_masked_merge(my_array) 
    real, intent(in) :: my_array(:) 
    real, allocatable :: masked(:) 

    masked = MERGE(my_array, 0., my_array<=15.) 
    ! ... 
end subroutine 

То есть, merge решение может использовать автоматическое распределение. Конечно, бывают случаи, когда этого не нужно (например, при работе с большим количеством my_array с такого же размера: при проверке размеров массивов в этих случаях часто возникают накладные расходы): используйте masked(:) = MERGE(...) после обработки распределения (что может быть актуальным даже для кода вопроса).

Смежные вопросы