|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Всё про VBA class module
Время создания: 12.10.2019 20:23
Раздел: Разные закладки - VBA - Меню VB-справка
Запись: xintrea/mytetra_db_adgaver_new/master/base/1570882570soi4yq2z4d/text.html на raw.githubusercontent.com
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Всё про VBA class module Классовая борьба, одни классы побеждают, другие исключаются. Такова история Содержание
Краткое руководство по VBA Class Module
Class Module VBA позволяют пользователю создавать свои собственные объекты. Если вы не знакомы с объектами, я настоятельно рекомендую вам сначала ознакомиться с моей статьей Все об объектах VBA Objects. В таких языках, как C # и Java, классы используются для создания объектов. Class Module являются VBA-эквивалентом этих классов. Основное отличие состоит в том, что Class Module VBA имеют очень ограниченный тип наследования * по сравнению с классами на других языках. В VBA наследование работает аналогично интерфейсам ** в C # \ Java. В VBA у нас есть встроенные объекты, такие как Collection, Workbook, Worksheet и так далее. Целью Class Module VBA является предоставление нам возможности создавать собственные объекты. Давайте начнем эту статью с рассмотрения того, почему мы используем объекты в первую очередь. *Наследование использует существующий класс для создания нового класса. Использование объектов позволяет нам создавать наши приложения так же, как мы используем строительные блоки. Идея состоит в том, что код каждого объекта является автономным. Он полностью независим от любого другого кода в нашем приложении. Это похоже на то, как все строится с использованием кирпичей Lego. Существует много различных типов компонентов Lego. Например, блок, руль и лазер — это разные вещи. Они ведут себя совершенно независимо друг от друга. Но мы можем соединить их вместе, чтобы создать здание, транспортное средство, космическую станцию и так далее. Если вам все еще неясно, не волнуйтесь. В остальной части этой статьи мы разберем все это на простые термины. Преимущества использования объектов Рассматривая части нашего кода как блоки, мы получаем много больших преимуществ.
Недостатки использования объектов У большинства вещей в жизни есть свои плюсы и минусы. Использование Class Module VBA ничем не отличается. Ниже приведены недостатки использования Class Module для создания объектов.
*Если вы создаете приложение с использованием объектов, на его создание уйдет больше времени, поскольку вам придется тратить больше времени на планирование и проектирование. Однако в долгосрочной перспективе это сэкономит вам огромное количество времени. Вашим кодом будет легче управлять, обновлять и использовать повторно. Создание простого Class Module Давайте рассмотрим очень простой пример создания Class Module и использования его в нашем коде. Чтобы создать Class Module, мы щелкаем правой кнопкой мыши в окне Project и затем выбираем Insert и Class Module. Наш новый класс называется Class1. Мы можем изменить имя в окне свойств, как показано на следующем скриншоте. Давайте изменим имя модуля класса на clsCustomer. Затем мы добавим переменную в Class Module следующим образом.
Теперь мы можем использовать этот Class Module в любом модуле (стандартном или классе) в нашей рабочей книге. Например:
Люди, которые плохо знакомы с использованием классов и модулей классов VBA, часто путаются между тем, что такое класс и что является объектом. Давайте посмотрим на пример из реального мира. Думайте о предмете массового производства как кофейная кружка. Дизайн кружки создается в первую очередь. Затем тысячи кофейных кружек создаются из этого дизайна. Это похоже на работу Class Module и объектов. Class Module можно рассматривать как дизайн. Объект можно рассматривать как элемент, созданный из дизайна. Ключевое слово New в VBA — это то, что мы используем для создания объекта из Class Module. Например:
Примечание. Мы не используем New для таких элементов, как Workbooks и Worksheets. См. Когда New не требуется для получения дополнительной информации. Class Module VBA против обычных модулей VBA Написание кода в Class Module почти такое же, как написание кода в обычном модуле. Мы можем использовать тот же код, который мы используем в обычных модулях. То, как этот код используется, сильно отличается. Давайте посмотрим на два основных различия между классом и обычным модулем. Это часто вызывает путаницу у новых пользователей. Разница 1 — Как используются модули Если вы хотите использовать подпрограмму / функцию и т.д. Из Например, представьте, что у нас есть два идентичных Sub PrintCustomer. Один находится в Class Module, а другой — в обычном модуле…
Вы заметите, что коды абсолютно одинаковые. Чтобы использовать подпрограмму PrintCustomer из Class Module, вы должны сначала создать объект этого типа
Чтобы использовать PrintCustomer из обычного модуля, вы можете вызвать его напрямую
Когда вы создаете переменную в обычном модуле, существует только одна ее копия. Для Class Module существует одна копия переменной для каждого создаваемого вами объекта. Например, представьте, что мы создаем переменную StudentName как в классе, так и в обычном модуле.
Для обычной переменной модуля в нашем приложении будет только одна копия этой переменной.
Для Class Module новая копия переменной StudentName создается каждый раз, когда создается новый объект.
Когда вы полностью поймете Class Module VBA, эти различия будут казаться очевидными. В Class Module есть четыре разных предмета. Это:
Вы можете видеть, что они все или функции, подпрограммы или переменные. Давайте кратко рассмотрим некоторые примеры, прежде чем разбираться с ними по очереди.
Теперь, когда мы увидели примеры, давайте рассмотрим каждый из них по очереди. Методы относятся к процедурам класса. В VBA есть процедуры и функции. Как и переменные-члены, они могут быть Public или Private. Давайте посмотрим на пример:
Мы можем использовать Class Module clsSimple следующим образом
Переменная-член очень похожа на обычную переменную, которую мы используем в VBA. Разница в том, что мы используем Public или Private вместо Dim.
Примечание: Dim и Private делают одно и то же, но соглашение заключается в том, чтобы использовать Dim в sub / functions и использовать Private за пределами sub / functions. Ключевое слово Public означает, что переменная может быть доступна вне Class Module. Например:
В приведенном выше примере мы не можем получить доступ к Балансу, потому что он объявлен, как Частный. Мы можем использовать только приватную переменную внутри Class Module. Мы можем использовать функцию / подпрограмму в Class Module, например:
Считается плохой практикой иметь публичные переменные-члены. Это потому, что вы позволяете коду вне объекта мешать работе класса. Цель использования классов состоит в том, чтобы скрыть происходящее от вызывающего. Чтобы пользователь не общался напрямую с нашими переменными-членами, мы используем Свойства.
Обычный формат для свойств выглядит следующим образом:
Мы уже видели, что свойство это просто тип sub. Назначение свойства — позволить вызывающей стороне получать и устанавливать значения. Почему мы не можем просто сделать переменные общедоступными и использовать их напрямую? Давайте объясним с некоторыми примерами. Представьте, что у нас есть класс, который ведет список стран. Мы могли бы сохранить список в виде массива:
Когда пользователь хочет получить количество стран в списке, он может сделать это:
С приведенным выше кодом есть две основные проблемы
Для решения этих проблем мы можем создать функцию, возвращающую количество стран:
Затем мы используем это так
Этот код решает две проблемы, которые мы перечислили выше. Мы можем изменить наш массив на коллекцию, и код вызывающего абонента все равно будет работать. Например:
Вызывающий не замечает, как хранятся страны. Все, что нужно знать вызывающему — это то, что функция Count будет возвращать количество стран. Как мы только что видели, подпрограмма или функция обеспечивает решение вышеуказанных проблем. Однако использование свойства может обеспечить более элегантное решение. Использование свойства вместо Function/Sub Вместо создания функции Count мы можем создать свойство Count. Как вы можете видеть ниже, они очень похожи:
В этом сценарии нет большой разницы между использованием свойства и использованием функции. Тем не менее, есть различия. Обычно мы создаем свойство Get и Let так:
Использование Let позволяет нам рассматривать свойство, как переменную. Таким образом, мы можем сделать это:
Второе отличие состоит в том, что использование Let и Get позволяет нам использовать одно и то же имя при обращении к свойству Get или Let. Таким образом, мы можем использовать свойство, как переменную. Это цель использования свойств над подпрограммой и функцией.
Если мы использовали функцию и подпрограмму, то мы не можем получить поведение переменной. Вместо этого мы должны вызвать две разные процедуры, например:
Вы также можете видеть, что когда мы использовали Let, мы можем присвоить значение, как переменную. Когда мы используем SetTotalCost, мы должны были передать его в качестве параметра.
Есть три типа свойств. Мы уже видели Get и Let. Но мы еще не рассмотрели Set. Set похож на Let, но он используется для объекта (подробнее об этом см. Назначение объектов VBA). Первоначально в Visual Basic ключевое слово Let использовалось для назначения переменной. На самом деле, мы можем использовать его, как захотим.
Поэтому мы используем Let, чтобы присвоить значение переменной, и мы используем Set, чтобы назначить объект переменной объекта.
В следующем примере мы используем свойства Get и Let для строковой переменной
Затем мы можем использовать свойства Name так:
В следующем примере мы используем свойства Get и Set для переменной объекта
Затем мы можем использовать свойства так:
Мы используем свойство Get, чтобы вернуть значения для обоих элементов. Обратите внимание, что даже если мы используем свойство Get для возврата коллекции, нам все равно нужно использовать ключевое слово Set для его назначения. Class Module имеет два события:
В объектно-ориентированных языках, таких как C ++, эти события называются Конструктором и Деструктором. В большинстве языков вы можете передавать параметры конструктору, но не в VBA. Мы можем использовать Class Factory, чтобы обойти эту проблему, как показано ниже. Давайте создадим очень простой Class Module с именем clsSimple с событиями Initialize и Terminate.
В следующем примере мы используем Dim и New для создания объекта. В этом случае oSimple не создается, пока мы не ссылаемся на него в первый раз, например:
Когда мы используем Set и New вместе, поведение отличается. В этом случае объект создается при использовании Set, например:
Примечание: Для получения дополнительной информации о различиях между использованием New с Dim и использованием New с Set см. Тонкие различия Dim и Set Как я уже говорил ранее, вы не можете передать параметр в Initialize. Если вам нужно сделать это, вам нужна функция, чтобы сначала создать объект.
Мы расширим CreateSimpleObject в Примере 2, чтобы создать фабрику классов. Событие Terminate наступает при удалении класса. Это происходит, когда мы устанавливаем значение Nothing.
Если мы не установим объект в Nothing, VBA автоматически удалит его, когда он выйдет из области видимости. Это означает, что если мы создадим объект в процедуре, когда эта процедура завершится, VBA удалит все созданные объекты.
В этом примере мы рассмотрим очень распространенное использование Class Module. Представьте, что у нас есть следующие данные: Мы хотим читать альбомы по разным годам, а затем создавать различные отчеты. Мы могли бы использовать для этого 2D-массив или коллекцию коллекций, например:
Как вы можете себе представить, этот код очень быстро запутался. К счастью для нас, у нас есть Class Module VBA, чтобы сделать нашу жизнь проще. Мы можем создать Class Module для хранения элементов.
Каждый раз, когда мы хотим добавить запись, мы можем сделать это следующим образом:
Как видите, это делает наш код более читабельным. Понятно, для чего используются Artist, Title и т.д. Затем мы можем легко использовать эти данные для создания отчетов, записи в файлы и т.д.
Ниже приведен полный код для этого примера
В этом примере мы пойдем дальше. Мы собираемся взглянуть на некоторые хитрые приемы при использовании объектов. Представьте, что у вас есть список продуктов, как на картинке ниже. Продукты имеют разные поля, поэтому нам нужно использовать разные модули классов для каждого типа продуктов. Один тип для строки Книги, один тип для строки Фильмы. Сначала мы создадим наши модули классов. Они очень похожи для обоих типов продуктов.
Как видите, единственная реальная разница — это инициализация. Когда мы читаем каждую запись, нам нужно определить, книга это или фильм. Затем мы создаем соответствующий объект. Представьте, что нам нужно создать переменную для каждого типа, например:
Если бы у нас было много разных типов, это было бы действительно очень грязно. Хорошей новостью является то, что нам нужно использовать только одну переменную! В VBA мы можем объявить переменную как вариант. Когда мы используем Variant, мы, по сути, говорим: «Мы определим тип переменной во время выполнения кода». Это очень полезно при работе с объектами и позволяет нам избежать использования одной переменной, например:
Это действительно полезно, так как нам нужна только одна переменная, независимо от того, сколько у нас объектов. Второе преимущество использования Variant заключается в следующем. Если у каждого Class Module есть подпрограмма / функция с одинаковым именем и параметрами, мы можем использовать одну и ту же переменную для ее вызова. Представьте, что в clsBook есть функция InitBook, а в clsFilm есть функция InitFilm. Нам нужно сделать это:
Однако, если они имеют одинаковое имя, например, Init, мы можем заменить строки кода If \ ElseIf одной строкой:
Теперь мы можем создать функцию для создания соответствующего объекта. В объектно-ориентированном программировании мы имеем то, что называется фабрикой классов. Это просто функция, которая создает объект на основе заданного типа. Ранее мы видели, что событие Initialize не принимает параметры. Мы можем позвонить в Init на фабрике классов, чтобы обойти эту проблему. Полный код для функции ClassFactory здесь:
Это следующее наше начало. В этом разделе мы читаем таблицу и передаем диапазон в ClassFactory. Создает объект, передает диапазон в метод Parse объекта. Затем он возвращает объект, который мы добавляем в нашу коллекцию.
Мы также можем использовать вариант объекта для печати элементов. Пока оба объекта имеют подпрограмму с одинаковым именем и параметрами (например, PrintToImmediate), мы можем вызывать ее, используя тип Variant.
На этом я заканчиваю свою статью о Class Module VBA. В этой статье мы рассмотрели части Class Module VBA и два примера, в которых вы могли бы их использовать. Важно понимать, что классы и объекты — это обширная тема. Существует множество типов объектов, которые вы можете создавать, и способы их использования. Если вы планируете использовать Class Module, то я советую начать с основ и ознакомиться с тем, как создать простой. Как только вы освоите основы, вам будет намного легче переходить к более сложным сценариям. Источник |
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Так же в этом разделе:
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|