Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Программирование на BASIC / Visual Basic / Учебно-методическое пособие по изучению Visual Basic for Applications (VBA).doc
Скачиваний:
207
Добавлен:
02.05.2014
Размер:
1.55 Mб
Скачать

Часть 7. Создание и использование функций и функций-процедур

Из этой части вы узнаете как создавать собственные пользовательские функции, как сделать так, чтобы ваши собственные функции были доступны рабочим листам Excel.

Лабораторная работа № 7. Функции-процедуры и определенные

пользователем функции

Цель занятия: Уметь создавать функции-процедуры и определенные

пользователем функции. Материалы к занятию: MS Excel 2003.

Создание функций и функций-процедур

Функция-процедура (или функция) – это особый вид процедуры VBA, возвращающей результат. Пользовательские функции, как и встроенные функции VBA, могут иметь необязательные и именованные аргументы. Функции можно использовать для обеспечения значениями выражений (присваивания) или в качестве аргументов других функций и процедур.

С «точки зрения» Excel используемые им функции-процедуры VBA, являются определенными пользователем функциями (user-defined functions). Этот термин позволяет отличать функции, написанные пользователем, от встроенных функций Excel. Хотя все определенные пользователем функции являются также функциями-процедурами, не все функции-процедуры отвечают требованиям определенной пользователем функции.

Функции-процедуры с некоторыми ограничениями на их действия называются определенными пользователем функциями (или сокращенно UDF user-defined functions), и только их может использовать Excel в формуле ячейки рабочего листа.

Все ограничения определенных пользователем функций происходят из одного базового ограничения: UDF не может никаким образом изменять среду Excel. Это означает, что определенная пользователем функция не может выбирать, вставлять, удалять или форматировать никакие данные в рабочем листе, таблице или другом листе. UDF также не может добавлять, удалять или переименовывать листы или рабочие книги, не может изменять экранное представление и так далее. Например, нельзя использовать функцию-процедуру как определенную пользователем функцию в Excel, если она выделяет ячейки или изменяет каким-то образом текущий рабочий лист.

Кроме того, UDF не может устанавливать свойства объекта или использовать методы объекта; в большинстве случаев установка свойств объекта или использование его методов приводят к изменениям в среде Excel (объекты, методы и свойства описываются в части 6). Определенная пользователем функция может осуществлять выборку значений свойств объекта и выполнять любые методы объекта, которые не изменяют среду Excel.

99

Следует помнить о том, что ни VBA, ни Excel не отображают сообщение об ошибке, если в качестве UDF используется функция, в которой нарушены правила для определенных пользователем функций. Такая функция просто не может возвращать результат. Например, при попытке вставить значение в рабочий лист Excel, используя функцию-процедуру, нарушающую правила для определенных пользователем функций, ячейка с такой функцией отображает Excel-сообщение об ошибке #VALUE!, обозначающее, что функция или формула для этой ячейки не может возвращать допустимый результат.

Функция-процедура – это наиболее общий термин для создаваемых пользователем функций; термин «определенная пользователем функция» описывает определенный тип функции-процедуры, который может использовать Excel.

Функция-процедура имеет следующий синтаксис:

Function Name ([Arglist]) [As Type]

' VBA Statements

[Name = expression] End Function

Каждая функция-процедура начинается ключевым словом Function, за которым следует имя функции, Name представляет имя, выбранное для этой функции. При написании имен функций необходимо соблюдать те же правила, что и при написании имен других идентификаторов в VBA: они должны начинаться с буквы, не могут содержать пробелов или каких-либо символов арифметических, логических операторов или операторов отношения и не могут дублировать ключевые слова VBA. После имени функции следует список ее аргументов, который заключается в круглые скобки. Здесь Arglist представляет список аргументов функции и является необязательным. Туре – любой тип возвращаемого значения функции. Если только не определяется иначе, результат, который возвращает функция-процедура, имеет тип Variant. Необязательный элемент синтаксиса Name = expression представляет присваивание функции (function assignment), которое указывает VBA, какое значение должна возвращать функция. Хотя эта часть функции является необязательной, следует всегда включать оператор присваивания в функции-процедуры. Наконец, объявление функции заканчивается ключевыми словами End Function.

Даже если функция не имеет аргументов, как VBA-функции Now, Date и Time, в объявлении функции необходимо использовать круглые скобки. Как вы уже знаете, информация встроенным функциям VBA передается заданием значений в списке аргументов функции. При объявлении функции-процедуры необходимо указывать имя каждого аргумента, передаваемого функции; имена аргументов в списке следует отделять друг от друга запятой и писать в соответствии с правилами, применяемыми к любому идентификатору VBA.

Имена аргументов имеют ту же область действия, что и переменные, объявляемые локально в функции-процедуре, то есть недоступны вне функции-процедуры, в списке аргументов которой они объявляются.

VBA запрещает присваивание несовместимого типа результату функции в

100

любой функции-процедуре, которая имеет объявленный тип данных для ее результата. Если, например, вы ошибочно написали оператор присваивания функции так, что присваивается, допустим, тип Integer результату функции с объявленным типом String, то VBA отображает ошибку несовпадения типа. В случае присваивания типа данных, который не является тем же, что объявленный возвращаемый тип для функции-процедуры, но является совместимым, то VBA преобразует значение типа, определенного для функции при возврате результата функции. Например, если присваивается тип Double функции, результат которой был объявлен как Long, то VBA не выдает никакой ошибки, а просто преобразует Double в тип Long (при возвращении результата функции).

Объявление типа функции имеет еще один результат: если функция-процедура заканчивается без выполнения оператора присваивания функции, VBA возвращает строку нулевой длины для функций типа String и 0 – для функций-процедур, возвращающих численный тип. Нетипизированная функция-процедура, которая заканчивается без выполнения оператора присваивания функции, возвращает результат типа Variant, содержащий специальное значение Empty.

Если только не было определено иначе, VBA передает все аргументы в функцию-процедуру как типы Variant. Можно объявлять определенные типы данных для каждого аргумента в списке аргументов. Аргументы с определенными типами используются по тем же знакомым причинам, по каким используются типизированные переменные или результаты функции. Для объявления определенных типов аргументов функции-процедуры, используйте ключевое слово As, за которым следует имя нужного типа данных после имени аргумента в списке аргументов.

Передача аргументов по ссылке и по значению

VBA передает информацию в процедуру-функцию с помощью аргументов и делает это двумя способами: по ссылке и по значению. По умолчанию VBA передает функции все аргументы по ссылке. При передаче аргументов по ссылке VBA фактически передает адреса величин, указанных в списке аргументов при вызове функции. Это означает, что если функция в процессе работы изменит значение одного из своих аргументов, то и исходные данные, передаваемые в качестве этого аргумента, изменятся.

При передаче аргумента по значению, VBA делает копию исходных данных и передает функции эту копию для обработки. При изменении значения аргумента, переданного по значению, изменяется только переданная функции копия; исходные данные не изменяются. Передача данных по ссылке позволяет изменить исходные данные, переданные функции через аргумент; а передача с помощью значения не позволяет изменять значение исходных данных.

Для того чтобы обозначить метод передачи аргумента – по ссылке или по значению, – перед этим аргументом следует вставить ключевое слово ByRef (по ссылке) или ByVal (по значению).

Использование функций-процедур в VBA

Используйте собственные функции-процедуры в операторах VBA так же, как любые встроенные функции VBA; все правила и условия по использованию

101

встроенных функций применимы к пользовательским функциям-процедурам. Помните, что при вызове функции необходимо включать список аргументов в круглых скобках, если только вы не собираетесь игнорировать результат функции. Как и в случае со встроенными функциями VBA, можно игнорировать результат вашей собственной функции, хотя это редко бывает необходимо. Если нужно использовать именованные аргументы в ваших собственных функциях-процедурах, просто используйте имена из списка аргументов в объявлении функции-процедуры. Если вам трудно запомнить все именованные аргументы для одной из своих функций, убедитесь, что свойство Auto Quick Info (краткие сведения) включено. Если это так, Редактор VB отображает всплывающее окно с перечнем именованных аргументов вашей функции, как для встроенных функций VBA.

Использование оператора Exit

Для того чтобы функция прекратила выполнение, используется форма VBA-оператора Exit. Оператор Exit имеет следующий синтаксис:

Exit Function

Exit Function используется для окончания функции.

Задание. Напишите процедуру для нахождения функции

ax -bx f (x,a,b) = . Вычисления показательной функции оформить в виде

1+ ab

функции. Числа x, a, b -вещественные.

Для этого:

ь введите функцию и процедуру (листинг 20):

Листинг 20 Использование Excel-функции МАКС

1 Function pok (ByVal a As Double, b As Double)

2 pok = a ^ b

3 End Sub 4

5 Sub List7_20 ()

6 Dim a As Double, b As Double, x As Double, f As Double 7

  1. x = CDbl(InputBox("Введите x" , "Исходные данные"))

  2. a = CDbl(InputBox("Введите a" , "Исходные данные"))

  3. b = CDbl(InputBox("Введите b" , "Исходные данные"))

  4. f = (pok(a,x) - pok(b,x)) / (1 + pok(a,b))

  5. MsgBox f , , "Результат"

13 End Sub

В строке 1 содержится объявление функции pok, начинающееся с обязательного ключевого слова Function. После имени функции открываются круглые скобки, что указывает VBA на начало списка аргументов. Далее следует

102

имена аргументов (a, b). Имена аргументов сообщают VBA, что функции-процедуре при ее вызове должны передаваться два аргумента (a - по значению, b - по ссылке). Строка 2 функции pok - это строка, которая выполняет всю (пока небольшую) работу функции и также содержит аргумент функции для pok. При

вычислении выражения ab VBA присваивает результат имени функции pok. pok

возвращает значение выражения ab. В строке 3 функция заканчивается ключевыми словами End Function. После выполнения этой строки VBA возвращается к оператору процедуры, вызвавшему функцию pok, и вставляет результат функции pok в этот оператор в том месте, где появляется имя функции.

После того как тип аргумента объявлен, VBA при вызове функции pok допускает в качестве аргумента появление только значений типа Double. Вызов pok с каким-либо другим типом (даже Variant) в качестве аргумента вызывает ошибку несовпадения типа (конкретнее, несовпадение типа аргумента argument type mismatch).

Использование инструмента Object Browser для нахождения функций-процедур

Если вы не можете вспомнить, в каком модуле сохранили некоторую функцию, можно использовать Object Browser для определения того, какие из ваших функций процедур доступны в данный момент, и для быстрого отображения исходного VBA-кода вашей функции.

Вы уже знаете, как использовать Object Browser для отображения доступных функций VBA или функций host-приложений. Раскрывающийся список Project/Library (Проект/Библиотека) отображает все открытые в данный момент файлы приложения, как и всегда присутствующую опцию VBA. Для отображения пользовательских функций (и других процедур) в определенном проекте VBA (рабочей книге Excel или каком-либо другом документе host-приложения) выполняйте следующие шаги:

^выберите наименование проекта в раскрывающемся списке Project/Library (в Excel подобный элемент называется VBAProject). Окно Project Explorer указывает имя файла, в котором сохранен проект (в круглых скобках после имени проекта);

  • выберите модуль в списке Classes. После этого список Members of<class> (Компонент) содержит перечень всех процедур и функций, объявленных в выбранном модуле;

  • выберите функцию или процедуру, исходный код которой необходимо просмотреть, в списке Members of<class>;

  • щелкните на кнопке L&l View Definition (Описания) для отображения исходного кода функции или процедуры. Редактор VB открывает соответствующий модуль и помещает курсор на первую строку после объявления функции или процедуры.

Использование функций пользователя в рабочих листах Excel

Чтобы использовать свои функции (определенные пользователем) в Excel, вводите имя функции и ее аргументы как формулу в ячейку рабочего листа так

103

же, как вы вводите любую встроенную функцию Excel. Если вы не можете запомнить имя определенной пользователем функции или ее аргументы, можно найти эту функцию в списке Мастера функций для категории Определенные пользователем. Отобразить диалоговое окно Мастер функций Excel можно, выбирая в меню Вставка/Функция….

Если при использовании определенной пользователем функции (UDF) в ячейке рабочего листа отображаемым результатом является значение ошибки #VALUE!, внимательно проверьте код в вашей функции-процедуре, чтобы убедиться, что он не нарушает каких-либо правил для определенных пользователем функций.

Определенная пользователем функция, которая перевычисляется при каждом изменении любой ячейки в рабочем листе Excel, называется изменяющейся функцией. Чтобы пометить UDF как изменяющуюся, добавьте следующий оператор к функции сразу за ее объявлением:

Application.Volatile

Этот VBA-оператор помечает UDF как изменяющуюся функцию, и такая функция на самом деле является особым типом процедуры. Эта процедура называется методом (method), принадлежащим Excel. Поскольку метод принадлежит Excel, необходимо при использовании метода Volatile задавать объект Application, точно так же, как необходимо задавать объект Application при использовании функции Excel в операторе VBA.

Однако не следует злоупотреблять методом Application.Volatile. Если все функции рабочего листа будут изменяющимися, это может привести к ненужным перевычислениям, что увеличивает общее время, необходимое для перевычисления рабочего листа.

Упражнение

Вставьте функцию pok в лист Excel и сделайте ее изменяющейся функцией.

Контрольные вопросы

  1. Чем отличается процедура-функция от любой другой процедуры, которую вы создаете?

  2. Чем отличается процедура-функция от определенной пользователем функции?

  3. Какими требованиями должна удовлетворять определенная пользователем функция?

  4. Что такое присваивание результата функции?

  5. Когда и почему следует передавать аргументы функции по значению?

Соседние файлы в папке Visual Basic