Функция пользователя определяется между операторами:
DEF FN...END DEF
Рассмотрим пример. Определим функцию пользователя –арксинус, которого нет в перечне стандартных. Для его определения используем стандартные функции ATN (арктангенс) и SQR (квадратный корень), а также математическое соотношение:
ARCSIN(X) = ATN(X / SQR(-X * X + 1)).
Пример:
DEF FNARCSIN (x) = ATN(x / SQR(1 - x ^ 2))
INPUT "Введи число из промежутка ]-1; 1["; a
PRINT "Арксинус этого числа есть "; FNARCSIN(a); " радиана."
|
В этой программе не определена функция в точках –1 и 1. Для её определения надо ввести дополнительные условия. В этом случае функция пользователя определяется в нескольких рядах программы.
DEF FNARCSIN (x)
SELECT CASE x
CASE 1 'для х=1
FNARCSIN = 2 * ATN(1) 'arcsin=pii/2
CASE -1 'для x = -1
FNARCSIN = -2 * ATN(1) 'arcsin=-pi/2
CASE ELSE
FNARCSIN = ATN(x / SQR(1 - x ^ 2))
END SELECT
END DEF
INPUT "Введи число из отрезка [-1; 1]"; a
PRINT "Арксинус равен "; FNARCSIN(a); " радиан."
|
PRINT " или "; 180*FNARCSIN(arv)/FNPII; " градусов."
Используя следующие математические соотношения, можно определить и другие математические функции:
Секанс
| Sec(X) = 1 / Cos(X)
|
Косеканс
| Cosec(X) = 1 / Sin(X)
|
Котангенс
| Cotan(X) = 1 / Tan(X)
|
Арксинус
| Arcsin(X) = Atn(X / Sqr(-X * X + 1))
|
Арккосинус
| Arccos(X) = Atn(-X / Sqr(-X * X + 1)) + 2 * Atn(1)
|
Арксеканс
| Arcsec(X) = Atn(X / Sqr(X * X – 1)) + Sgn((X) – 1) * (2 * Atn(1))
|
Арккосеканс
| Arccosec(X) = Atn(X / Sqr(X * X - 1)) + (Sgn(X) – 1) * (2 * Atn(1))
|
Арккотангенс
| Arccotan(X) = Atn(X) + 2 * Atn(1)
|
Гиперболический синус
| HSin(X) = (Exp(X) – Exp(-X)) / 2
|
Гиперболический косинус
| HCos(X) = (Exp(X) + Exp(-X)) / 2
|
Гиперболический тангенс
| HTan(X) = (Exp(X) – Exp(-X)) / (Exp(X) + Exp(-X))
|
Гиперболический секанс
| HSec(X) = 2 / (Exp(X) + Exp(-X))
|
Гиперболический косеканс
| HCosec(X) = 2 / (Exp(X) – Exp(-X))
|
Гиперболический котангенс
| HCotan(X) = (Exp(X) + Exp(-X)) / (Exp(X) – Exp(-X))
|
Гиперболический арксинус
| HArcsin(X) = Log(X + Sqr(X * X + 1))
|
Гиперболический арккосинус
| HArccos(X) = Log(X + Sqr(X * X – 1))
|
Гиперболический арктангенс
| HArctan(X) = Log((1 + X) / (1 – X)) / 2
|
Гиперболический арксеканс
| HArcsec(X) = Log((Sqr(-X * X + 1) + 1) / X)
|
Гиперболический арккосеканс
| HArccosec(X) = Log((Sgn(X) * Sqr(X * X + 1) + 1) / X)
|
Гиперболический арккотангенс
| HArccotan(X) = Log((X + 1) / (X – 1)) / 2
|
Логарифм при основании N.
| LogN(X) = Log(X) / Log(N) или LogN(N,X) = Log(X) / Log(N)
|
Функция пользователя может обрабатывать текст. Рассмотрим например функцию пользователя, которая убирает пустые места (пробелы), как справа, так и слева.
DEF FNTRIM$ (tekst$) = LTRIM$(RTRIM$(tekst$))
a$ = " @ "
PRINT "joosep" + FNTRIM$(a$) + "kuskil.ee"
|
FUNCTION...END FUNCTION
Удобнее оформлять функцию пользователя в виде отдельного модуля.
Для этого надо:
1. Взять из меню EDIT команду New Function...
2. Напечатать имя функции (Первая – буква, без пробелов, английскими буквами и цифрами)
3. В открывшемся окне между FUNCTION и END FUNCTION напечатать описание функции.
4. Возвратится в основную программу, взяв из меню View команду Subs... и далее выбрав название своей программы.
Отличием от предыдущего случая является то, что перед названием программы не должны быть буквы FN и описание модуля функции не видно в основной программе.
Общий вид функции пользователя:
FUNCTION имя [(аргументы)] [STATIC]
[команды]
имя = значение
[EXIT FUNCTION]
[команды]
END FUNCTION
|
Если нет слова STATIC, то значения переменных обнуляются. А если есть слово STATIC, то сохраняются промежуточные значения переменных при многократном использовании программы.
EXIT FUNCTION даёт возможность прервать выполнение программы и выйти из неё.
Приведём пример создания функции пользователя HYPOTENUUS, у которой 2 аргумента a и b. Значение функции находим с помощью теоремы Пифагора.
Для этого делаем следующее:
1. Выбираем Edit->New Function..
2. Даём имя hypotenuus
3. Получаем:
FUNCTION hypotenuus
END FUNCTION
|
4. Теперь пишем аргументы в первую строку и формулу для гипотенузы.
FUNCTION hypotenuus (a, b)
hypotenuus = SQR(a ^ 2 + b ^ 2)
END FUNCTION
|
5. Возвращаемся в основную программу View->Subs...и пробуем использовать функцию пользователя.
INPUT "Введи длину катета";a
INPUT "Введи длину второго катета";b
PRINT "Длина гипотенузы равна";hypotenuus(a,b)
|
После сохранения программы, созданную функцию пользователя можно использовать только вместе с этой программой. После сохранения добавляется фраза в начало программы DECLARE FUNCTION... это вспомогательная фраза для, которую делает редактор QBASIC. При редактировании функции пользователя, эту фразу надо стирать.
Создадим программу, которая решает систему линейных уравнений относительно x и y.
A*x+b*y=c
D*x+e*y=f
У этой системы должно быть 6 аргументов (a, b, c, d, e, f) + ещё аргумент «какой», которым задаём, относительно чего решаем систему (x или y).
Договоримся. Что аргумент «какой» может принимать только 2 значения –1 (верное) или 0 (неверное) и в зависимости от этого получаем решение первого или второго уравнения.
Описание функции:
FUNCTION lvs (a, b, c, d, e, f, kumb)
'находим детерминант системы
d = a * e - b * d
'в зависимости от аргумента «какой» решаем систему
IF kumb THEN
lvs = (c * e - b * f) / d
ELSE
lvs = (a * f - d * c) / d
END IF
END FUNCTION
|
Однако возникают проблемы при d=0. Рассмотрим, как это решить с помощью оператора EXIT FUNCTION.
FUNCTION lvs (a, b, c, d, e, f, kumb)
d = a * e - b * d
IF d=0 THEN EXIT FUNCTION
IF kumb THEN
lvs = (c * e - b * f) / d
ELSE
lvs = (a * f - d * c) / d
END IF
END FUNCTION
|
При d=0, значение функции получактся равным 0, что неверно. Исправим это.
CLS
PRINT "Решение системы уравнений вида:"
PRINT "ax+by=c"
PRINT "ex+dy=f"
PRINT
INPUT "Введи аргументы первой системы (a,b,c)"; a, b, c
INPUT "Введи аргументы второй системы (d,e,f)"; d, e, f
PRINT
'если kumb=1, то решение первой системы
PRINT "x="; lvs(a, b, c, d, e, f, 1)
'если kumb=0, то решение второй системы
PRINT "y="; lvs(a, b, c, d, e, f, 0)
|
Создадим функцию пользователя, которая находит наибольший общий делитель (НОД) двух чисел.
FUNCTION SYT (arv1, arv2)
'запомним значения arv1 и arv2, чтобы их можно было в дальнейшем использовать
a=arv1
b=arv2
DO
IF a > b THEN a = a - b
IF b > a THEN b = b - a
LOOP UNTIL a = b
SYT = a
END FUNCTION
|
Приведём пример ещё одной программы сложения двух обыкновенных дробей.
PRINT "Вычислим: a/b+c/d"
INPUT "Введи значения (a,b)"; a, b
INPUT "Введи значения (c,d)"; c, d
'находим НОД
n = b * d
'и знаменатель
l = a * d + c * b
PRINT "Ответ:"; l; "/"; n
'используем функцию пользователя
s=SYT(n, l)
n = n / s
l = l / s
PRINT "Ответ:"; l; "/"; n
|
Чтобы использовать функцию пользователя, она должна быть определена в данной программе.
Одна функция пользователя может содержать внутри себя другую.
Например определим функцию пользователя VYK(a, b)=a*b/SYT(a, b).
FUNCTION VYK(a,b)
VYK=a*b/SYT(a,b)
END FUNCTION
|
При этом функция SYT(a,b) должна быть определена в этой программе.
Следующая функция пользователя выбирает из ”isikukood” дату рождения и оформляет её в виде: dd.mm.yy
FUNCTION ID2SYND$ (isikukood$)
KUUPAEV$ = MID$(isikukood$, 6, 2) + "."
KUUPAEV$ = KUUPAEV$ + MID$(isikukood$, 4, 2) + "."
KUUPAEV$ = KUUPAEV$ + MID$(isikukood$, 2, 2)
ID2SYND$ = KUUPAEV$
END FUNCTION
|
Основная программа:
INPUT "Введи свой код (isikukood):"; ID$
PRINT "Твоя дата рождения:" ID2SYND$(ID$)
|
Если последний пример сохранить и открыть затем в текстовом редакторе, например NotePad, то текст программы будет выглядить следующим образом и его можно распечатать в виде:
DECLARE FUNCTION ID2SYND$ (isikukood$)
INPUT " Введи свой код (isikukood):"; ID$
PRINT " Твоя дата рождения:"; ID2SYND$(ID$)
FUNCTION ID2SYND$ (isikukood$)
KUUPAEV$ = MID$(isikukood$, 6, 2) + "."
KUUPAEV$ = KUUPAEV$ + MID$(isikukood$, 4, 2) + "."
KUUPAEV$ = KUUPAEV$ + MID$(isikukood$, 2, 2)
ID2SYND$ = KUUPAEV$
END FUNCTION
|