با عرض سلام و وقت بخیر خدمت کاربران سایت پی وی لرن ، جلسه هجدهم از آموزش های دوره فرترن را ،با روال ها در فرترن آغاز می کنیم. همچنین زیر مجموعه در فرترن و نحوه فراخوانی آن ها را شرح می دهیم.یک رویه گروهی از عبارات است که یک کار مشخص را انجام می دهند و می توانند در برنامه شما فراخوانی شوند. اطلاعات (یا داده ها) به برنامه فراخوانی به عنوان آرگومان منتقل می شود.
به طور کلی دو روال وجود دارد :
یک تابع یک روش است که یک مقدار را باز می گرداند. تابع نباید استدلال های آن را اصلاح کند.
مقدار بازگشتی به عنوان مقدار تابع شناخته شده است و توسط نام تابع مشخص شده است.
سینتکس برای یک تابع به شرح زیر است :
1 2 3 4 | function name(arg1, arg2, ....) [declarations, including those for the arguments] [executable statements] end function [name] |
مثال زیر یک تابع به نام area_of_circle را نشان می دهد. که محدوده یک دایره با شعاع r را محاسبه می کند.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | program calling_func real :: a a = area_of_circle(2.0) Print *, "The area of a circle with radius 2.0 is" Print *, a end program calling_func ! this function computes the area of a circle with radius r function area_of_circle (r) ! function result implicit none ! dummy arguments real :: area_of_circle ! local variables real :: r real :: pi pi = 4 * atan (1.0) area_of_circle = pi * r**2 end function area_of_circle |
هنگامی که شما برنامه فوق را کامپایل و اجرا میکنید، نتیجه زیر تولید می شود :
1 2 | The area of a circle with radius 2.0 is 12.5663710 |
شما باید اسم ضمنی را در برنامه اصلی و همچنین رویه مشخص کنید.
آرگومان R در تابع فراخوانی شده با آرگومان جعلی فراخوانی می شود.
اگر می خواهید مقدار بازگشتی در نام دیگری از نام تابع ذخیره شود، می توانید از گزینه نتیجه استفاده کنید.
شما می توانید نام متغیر را باز گردانید مانند مثال زیر :
1 2 3 4 | function name(arg1, arg2, ....) result (return_var_name) [declarations, including those for the arguments] [executable statements] end function [name] |
زیر مجموعه در فرترن یک مقدار را نمیدهد، اما میتواند آرگومان هایش را تغییر دهد.
سینتکس
1 2 3 4 | subroutine name(arg1, arg2, ....) [declarations, including those for the arguments] [executable statements] end subroutine [name] |
شما باید با استفاده از عبارت فراخوانی، یک زیرمجموعه را فراخوانی کنید.
مثال زیر تعریف و استفاده از مبادله زیرمجموعه را نشان می دهد.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | program calling_func implicit none real :: a, b a = 2.0 b = 3.0 Print *, "Before calling swap" Print *, "a = ", a Print *, "b = ", b call swap(a, b) Print *, "After calling swap" Print *, "a = ", a Print *, "b = ", b end program calling_func subroutine swap(x, y) implicit none real :: x, y, temp temp = x x = y y = temp end subroutine swap |
هنگامی که کدهای بالا را کامپایل و اجرا کنید نتیجه زیرا مشاهده می کنید :
1 2 3 4 5 6 | Before calling swap a = 2.00000000 b = 3.00000000 After calling swap a = 3.00000000 b = 2.00000000 |
صفت هدف به شما اجازه می دهد تا مشخص کنید که کدام آزگومان در رویه استفاده می شود.
جدول زیر مقادیر صفت هدف را فراهم می کند:
مقدار | مکان مورد استفاده | توضیح |
in | (intent(in | به عنوان مقادیر ورودی استفاده می شود، در توابع تغییر نمی کند. |
out | (intent(out | به عنوان مقدار خروجی مورد استفاده قرار می گیرند، آنها دوباره رونویسی می شوند. |
inout | (intent(inout | آرگومان ها در هر دو مورد استفاده و رونویسی شده اند. |
مثال زیر این مفهوم را نشان می دهد :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | program calling_func implicit none real :: x, y, z, disc x = 1.0 y = 5.0 z = 2.0 call intent_example(x, y, z, disc) Print *, "The value of the discriminant is" Print *, disc end program calling_func subroutine intent_example (a, b, c, d) implicit none ! dummy arguments real, intent (in) :: a real, intent (in) :: b real, intent (in) :: c real, intent (out) :: d d = b * b - 4.0 * a * c end subroutine intent_example |
هنگامی که کدهای بالا را کامپایل و اجرا کنید نتیجه زیرا مشاهده می کنید :
1 2 | The value of the discriminant is 17.0000000 |
بازگشت زمانی رخ می دهد که زبان های برنامه نویسی به شما اجازه می دهند تا یک تابع زا درون تابع مشابه فراخوانی کنید. این فراخوانی مجدد تابع نامیده می شود.
وقتی یک رویه به خودی خود، به طور مستقیم یا غیرمستقیم، یک روش بازگشتی فراخوانی می شود. شما باید نوع رویه ها را با اصلاح کلمه قبل از اعلام آن، اعلام کنید.
وقتی یک تابع به صورت بازگشتی استفاده می شود، گزینه نتیجه باید استفاده شود.
در زیر یک مثال است که فاکتوریل را برای یک شماره داده شده با استفاده از یک روش بازگشتی محاسبه می کند :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | program calling_func implicit none integer :: i, f i = 15 Print *, "The value of factorial 15 is" f = myfactorial(15) Print *, f end program calling_func ! computes the factorial of n (n!) recursive function myfactorial (n) result (fac) ! function result implicit none ! dummy arguments integer :: fac integer, intent (in) :: n select case (n) case (0:1) fac = 1 case default fac = n * myfactorial (n-1) end select end function myfactorial |
هنگامی که یک فرایند درون یک برنامه قرار می گیرد، رویه درونی برنامه نامیده می شود. سینتکس برای محتوای رویه داخلی به شرح زیر است :
1 2 3 4 5 6 7 8 9 | program program_name implicit none ! type declaration statements ! executable statements . . . contains ! internal procedures . . . end program program_name |
مثال زیر این مفهوم را نشان می دهد :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | program mainprog implicit none real :: a, b a = 2.0 b = 3.0 Print *, "Before calling swap" Print *, "a = ", a Print *, "b = ", b call swap(a, b) Print *, "After calling swap" Print *, "a = ", a Print *, "b = ", b contains subroutine swap(x, y) real :: x, y, temp temp = x x = y y = temp end subroutine swap end program mainprog |
هنگامی که کدهای بالا را کامپایل و اجرا کنید نتیجه زیرا مشاهده می کنید :
1 2 3 4 5 6 | Before calling swap a = 2.00000000 b = 3.00000000 After calling swap a = 3.00000000 b = 2.00000000 |
به طور خلاصه روال ها در فرترن (Procedure): اين ها را برنامه نويس خود نوشته و می تواند در هر برنامه ای از آنها استفاده نموده و يا آنها را تغيير و يا اصلاح نمايد. با ما همراه باشید تا در جلسه بعد ماژول ها در فرترن را آموزش ببینید.