
Уокенбах Формулы в Excel
.pdfРеверсирование строки
Следующая функция REVERSETEXT возвращает текст ячейки в обратном порядке.
Function REVERSETEXT(text) As String
1 |
Возвращает аргумент в обратном порядке |
|
REVERSETEXT =StrReverse(text) |
End |
Function |
В этой функции используется функция VBA StrReverse. Приведенная ниже формула возвращает tfosorciM.
=REVERSETEXT("Microsoft")
Функции StrReverse нет в Excel до версии 2000. Таким образом, если эта функциявам нужна в ранних версиях Excel, необходимо написать собственную аналогичную функцию. Функция REVERSETEXT2 работает так же,каки функция REVERSETEXT.
Function REVERSETEXT2(text) As String
1 Возвращает аргумент в обратном порядке
'Используется в версиях до Excel 2000 Dim TextLen As Integer
Dim i As Integer TextLen = Len(text)
For i = TextLen To 1 Step -1
REVERSETEXT2 = REVERSETEXT2 & Mid(text, i, 1) Next i
End Function
В функции используется цикл For-Next с отрицательным значением Step. Буквы объединены (с помощью символа &, который является оператором конкатенации) дляформирования строки в обратном порядке.
Перетасовка текста
Следующая функция возвращает содержимое аргумента, но его символы расположены в случайном порядке. Например, если использовать Microsoft в качестве аргумента, то в результате может получиться oficMicro илистрока с другим порядком представления символов.
Function SCRAMBLE(text)
Dim |
TextLen As Integer |
|
Dim |
i As Integer |
|
Dim |
RandPos As Integer |
|
Dim |
Char As String * 1 |
|
Set |
text =text.Range("Al") |
|
TextLen = Len(text) |
||
For |
i = 1 To TextLen |
|
|
Char = Mid(text, i, 1) |
|
|
RandPos = Int((TextLen - 1 + 1 ) * Rnd + 1) |
|
|
Mid(text, |
i, 1) = Mid(text, RandPos, 1) |
|
Mid(text, |
RandPos, 1) = Char |
Next i
SCRAMBLE = text
End Function
Эта функция обрабатывает каждый символ, а затем заменяет его другим случайно выбранным символом.
550 |
Часть VI. Разработка пользовательскихфунк |
Действие функции Mid может показаться немного странным. Обратите внимание, что когда Mid стоит справа от оператора присвоения, то это функция. А когда Mid стоит слева от оператора присвоения, то это выражение. Обратитесь к справочной системе, чтобы подробно ознакомиться сназначением Mid.
Возвращение аббревиатуры
Функция ACRONYM возвращает первую букву каждого слова аргумента (в верхнем регистре). Например, следующая формула возвратит IBM:
=ACRONYM(International Business Machines) Листинг процедуры Function ACRONYM следующий:
Function ACRONYM(text) As String Возвращает аббревиатуру
Dim TextLen As Integer Dim i As Integer
text = Application.Trim(text) TextLen = Len(text)
ACRONYM = Left(text, 1) For i = 2 To TextLen
If Mid(text, i, 1) = Chr(32) Then
ACRONYM = ACRONYM & Mid(text, i + 1, 1) End If
Next i
ACRONYM = UCase(ACRONYM) End Function
В этой функции используется функция TRIM, чтобы удалить лишние пробелы в аргументе. Первый символ аргумента всегда является первым символом результата. Цикл For-Next проверяет каждый символ. Если символ является пробелом, то символ послепробела добавляется к результату. Затем результат преобразуется в верхний регистр с помощью функцииVBA UCase.
Соответствие текста шаблону?
Следующая функция возвращает TRUE, если строка совпадает сшаблоном, составленным из текста и специальных символов. Функция ISLIKE довольно проста и обычно используется вместе соператором VBA Like.
Function ISLIKE(text As String, pattern As String) As Boolean
1 |
Возвращает TRUE, если первый аргумент подобен второму |
|
If text Like pattern Then ISLIKE = True Else ISLIKE = False |
End |
Function |
В VBA поддерживаются следующие специальные символы:
? один любой символ
*нуль или несколько символов
# любая цифра (0-9)
[list] |
один любой символ в списке |
[! 1 i st] |
один любой символ вне списка |
Следующая формула возвращает значение TRUE, поскольку вопросительный знак (?) соответствует любому символу. Если бы первый аргумент равнялся Unit 12, то функция врезультате возвратила бы FALSE.
=ISLIKE ("Unitl";"Unit?")
Глава 25. Примеры пользовательских функций VBA |
551 |
Функция ISLIKE работает также исо значениями. Например, нижеприведенная формула возвращает значение TRUE, если ячейка А1 содержит значение, которое начинается с 1 и состоит из трех цифр.
= I S L I K E ( A 1 ; " 1 # # " )
Следующая формула возвращает значение TRUE, поскольку первый аргумент является символом, который находится всписке символов, определенном во втором аргументе.
=ISLIKE("a";"[aeiou]")
Если список символов начинается с восклицательного знака (!), тосравниваются символы вне списка. Например, следующая формула возвращает значение TRUE, поскольку первый аргумент является символом вне списка второго аргумента.
=ISLIKE("g";"[!aeiou]")
Использование оператора Like очень разносторонне. Более подробная информация оработе соператором Like приведена всправочной системе.
Содержится ли вячейке текст?
В главе 5 рассказывалось, как некоторые функции рабочего листа Excel становились временно ненадежными приуправлении текстом в ячейках. Приведенная ниже функция CELLHASTEXT возвращает значение TRUE, если в аргументе ячейки содержится текст или значение, форматированное как Text.
Function CELLHASTEXT(cell) As Boolean
1 |
Возвращает TRUE, если ячейка содержит строку |
|
' |
или имеет текстовый тип данных |
|
|
Dim |
UpperLeft As Range |
|
CELLHASTEXT = False |
|
|
Set |
UpperLeft = cell.Range("Al") |
|
If |
UpperLeft.NumberFormat = "@" Then |
|
|
CELLHASTEXT = True |
|
|
Exit Function |
|
End |
If |
If Not IsNumeric(UpperLeft) Then CELLHASTEXT = True
Exit Function End If
End Function
Следующая формула возвращает значение TRUE, если вячейке А1 содержится строка или если ячейка отформатирована как Text.
=CELLHASTEXT(Al)
Извлечение n-ого элемента строки
Функция EXTRACTELEMENT является пользовательской функцией рабочего листа, которая извлекает элемент из текстовой строки, основываясь на определенном символеразделителе. Предположим, что вячейке А1 содержится такой текст:
123-456-789-9133-8844
Например, следующая формула возвращает строку 9133, что соответствует четвертому элементу строки. В строке вкачестве разделителя используется дефис (-).
=EXTRACTELEMENT(Al;4;"-")
552 |
Часть VI. Разработкапользовательских функ |
Вфункции EXTRACTELEMENT используется три аргумента:
•Txt. Строка текста, из которой извлекается элемент. Это может быть строка из букв или ссылка на ячейку.
•п. Целое число, показывающее номер извлекаемого элемента.
•Separator. Символ, используемый в качестве разделителя.
Если в качестве символа-разделителя определить пробел, то несколько пробеловмогут восприниматься какодин пробел (почти всегда этотак, каки должно быть). Если п превышает количество элементов в строке,тофункция возвращает пустую строку.
В VBA-коде функция EXTRACTELEMENT выглядит так: |
|
Function EXTRACTELEMENT(Txt, n, Separator) As String |
|
1 |
Возвращает п-й элемент текстовой строки при разделении |
' |
ее определенным символом |
|
Dim AllElements As Variant |
|
AllElements = Split(Txt, Separator) |
|
EXTRACTELEMENT = AllElements(n - 1) |
End |
Function |
В этой функции использовалась функция VBA Split , которая возвращает массив variant , содержащий все элементы текстовой строки. Массив начинается с 0 (а не с 1), поэтому для обращения к нужному элементу следует писать п-1.
Функция S p l i t начала использоваться с Excel 2000. Если вами используется более ранняя версия Excel, то следует создать следующую функцию:
Function EXTRACTELEMENT2(Txt, n, |
Separator) |
As |
String |
|||||||
' |
Возвращает п-й |
элемент |
текстовой строки |
при |
разделении |
|||||
1 |
ее определенным |
символом |
|
|
|
|
|
|||
1 |
Используется |
в |
версиях |
до Excel |
2000 |
|
|
|||
|
Dim Txtl As |
String, |
TempElement |
As |
String |
|
||||
|
Dim ElementCount As |
Integer, |
i |
As |
Integer |
|
Txtl = Txt
'Если разделитель — пробел, удаляются повторяющиеся символы
If Separator = Chr(32) Then Txtl = Application.Trim(Txtl)
1
1
1
1
Добавление разделителя в конец строки
If Right(Txtl, Len(Txtl)) <> Separator Then _ Txtl = Txtl & Separator
Инициализация ElementCount = 0 TempElement = ""
Выделение каждого элемента For i = 1 To Len(Txtl)
If Mid(Txtl, i, 1} = Separator Then ElementCount = ElementCount + 1 If ElementCount = n Then
При нахождении выход EXTRACTELEMENT2 = TempElement Exit Function
Else
Глава 25. Примеры пользовательских функций VBA |
553 |
TempElement = ""
End If
Else
TempElement = TempElement & Mid(Txtl, i, 1)
End If
Next i
EXTRACTELEMENT2 = ""
End Function
Написание цифры прописью
Функция SPELLDOLLARS возвращает найденную в тексте цифру, написанную пропи-
сью — какэто делается на банковских чеках. |
Ш |
speMufctf» luoct.on xlt щтт^/ш^шшйтш? |
, |
jeisl*J |
||||
Например, приведенная ниже формула воз- |
||||||||
вращает строку One hundred twenty-three and |
|
А |
В |
__, __ |
С |
JD_ |
L_JT |
|
t |
*~ |
3 2 " |
" Thirty-Two and00/100 Dollars |
" * |
~* |
|||
2 |
|
37,56 |
Thirty-Seven and 56/100 Dollars |
|
||||
45/100 dollars. |
|
|
||||||
3 * |
-32 |
(Thirty-Two and00/100Dollars) |
|
|||||
|
4 |
|
-26.44 |
(Twenty-Six and44/100Dollars) |
|
|||
=SPELLDOLLARS(123,45) |
5 |
|
-4 |
(Four and 00/100Dollars) |
|
|
||
|
|
|
1.56 |
One |
and56/100 Dollars |
|
: |
|
На рис. 25.4 показаны примеры функции |
7 |
|
1 |
One |
and00/100 Dollars |
|
|
|
8 |
\ |
6.56 |
Six |
and56/100 Dollars |
|
|
||
SPELLDOLLARS. В столбце С содержатся фор- |
|
|
||||||
9 |
|
12.12 |
Twelve and 12/100 Dollars |
|
|
|||
10 |
1000000 |
One |
Million and00/100 Dollars |
|
||||
мулы, в которых используется эта функция. На- |
|
|||||||
1! |
10000000000 |
Ten |
Billion and00/100 Dollars |
|
— |
|||
пример, формула в ячейке С1 такая: |
12 |
|
|
|
|
|
|
|
13" |
|
|
|
|
|
|||
=SPELLDOLLARS(Al) |
14 |
|
|
|
|
|
||
M |
4 > M\sheetl/ |
|
lil |
i |
ЙП |
|||
|
|
|||||||
Обратите внимание, что отрицательные зна- |
|
|
|
|
||||
Рис. 25.4.Примеры функции SPELLDOLLARS |
||||||||
чения записываются прописью и заключаются в |
круглые скобки.
Функции подсчета и суммирования
В главе 7 приведено много примеров формул подсчета и суммирования ячеек по различным критериям. Если ни одна из формул для подсчета и суммирования не подходит, значит нужно создать собственную пользовательскую функцию. В этом разделе предлагаются три функции, выполняющие операции подсчета и суммирования.
Подсчет ячеек сопределенными значениями
Предположим, что нужно посчитать количество значений в промежутке между 6 и 12 в диапазоне Al: A100. Для этого воспользуемся формулой
= С Ч Ё Т Е С Л И ( А 1 : А 1 0 0 ; " < = 1 2 " ) - С Ч Ё Т Е С Л И ( A l : A 1 0 0 ; " < 6 " )
Эта формула корректно работает, но ее написание может вызвать затруднения. Формула подсчитает количество ячеек созначениями, меньше или равно 12,а затем вычтет количество ячеек созначениями, меньше 6.
Функция COUNTBETWEENобычно используется вместо приведенной выше формулы:
Function COUNTBETWEEN(rng, numl, num2)
' Вычисление количества значений между numl и num2 Dim CellCount As Integer
Dim cell As Range
Set rng = Intersect(rng.Parent.UsedRange, rng) CellCount = 0
554 |
Часть VI. Разработка пользовательских функций |
For Each cell In rng
If cell.Value >= numl And cell.Value <= num2 Then CellCount = CellCount + 1
Next cell
COUNTBETWEEN = CellCount End Function
Функция COUNTBETWEEN принимает три аргумента:
•rng. Диапазон
•numl. Нижний предел
•пшп2. Верхний предел
В этой функции используется функция Excel СЧЁТЕСЛИ, которая возвращает количество ячеек в rng, которое больше или равно numl и меньше или равно пшп2.
Подсчет видимых ячеек диапазона
Следующая функция COUNTVISIBLE принимает аргумент диапазона и возвращает количество непустых отображаемых ячеек диапазона. Ячейка считается скрытой, если она находится в скрытой строке или столбце.
Function COUNTVISIBLE(rng)
' |
Подсчет отображаемых ячеек |
||
|
Dim |
CellCount As Long |
|
|
Dim |
cell As Range |
|
|
Application.Volatile |
||
|
CellCount = 0 |
||
|
Set |
rng = Intersect(rng.Parent.UsedRange, rng) |
|
|
For |
Each cell In rng |
|
|
|
If Not IsEmpty(cell) Then |
|
|
|
If |
Not cell.EntireRow.Hidden And _ |
|
|
|
Not cell.EntireColumn.Hidden Then _ |
|
|
|
CellCount = CellCount + 1 |
|
|
End |
If |
|
Next cell |
||
|
COUNTVISIBLE = CellCount |
||
End |
Function |
|
Эта функция обрабатывает каждую ячейку диапазона, проверяя, является ли она пустой. Если ячейка непустая, то функция проверяет свойство Hidden строки и столбца ячейки. Если ни столбец, ни строка не являются скрытыми, то переменная CellCount увеличивается на 1.
При работе со средством Автофильтр или в режиме структуры вы можете обратиться к более удобной функции Excel ПРОМЕЖУТОЧНЫЕ. ИТОГИ (с первым аргументом 2 или 3). Однако функция ПРОМЕЖУТОЧНЫЕ. ИТОГИ работает некорректно, если ячейки скрыты вручную с помощью команд Формат^Строка^Скрыть или Формат^Столбец^Скрыть. В таком случае функция COUNVISIBLE является единственной альтернативой.
Суммирование видимых ячеек диапазона
Функция SUMVISIBLE основана на функции COUNTVISIBLE, о которой говорилось в предыдущем разделе. Эта функция принимает аргумент диапазона и возвращает сумму видимых ячеек диапазона. Ячейка считается скрытой, если она находится в скрытом столбце или строке.
Глава 25. Примеры пользовательских функций VBA |
555 |
Function SumVisible(rng)
' Суммирование только отображенных значений Dim CellSum As Long
Dim cell As Range Application.Volatile CellSum = 0
Set rng = Intersect(rng.Parent.UsedRange, rng) For Each cell In rng
If IsNumeric(cell) Then
If Not cell.EntireRow.Hidden And _ Not cell.EntireColumn.Hidden Then _
CellSum = CellSum + cell End If
Next cell
SumVisible = CellSum End Function
Скрывание и отображение строк и столбцов не приводит к выполнению пересчета рабочего листа. Поэтому, чтобы сделать пересчет, нужно нажать клавиши<Ctrl+Alt+F9>.
Функция Excel ПРОМЕЖУТОЧНЫЕ.ИТОГИ (с первым аргументом 9) также применяется для суммирования видимых ячеек в списке автофильтра. Однако функция ПРОМЕЖУТОЧНЫЕ. ИТОГИ работает некорректно, если в неотфильтрованном списке присутствуют скрытые ячейки.
Функции управления датами
В главе 6 предложено несколько полезных функций и формул Excel для вычисления дат, времени и временных периодов. В этом разделе приведены дополнительные функции для работы с датами.
Расчет следующего понедельника
Приведенная ниже функция NEXTMONTH принимает дату в качестве аргумента и возвращает дату следующего понедельника.
Function NEXTMONDAY(d As Date) As Date
1Возвращение следующего понедельника (Monday) NEXTMONDAY = d + 8 - WeekDay(d, vbMonday)
End Function
В этой функции используется функция VBA WeekDay, которая возвращает целое число, соответствующее дню недели для текущей даты (l=Sunday, 2=Moday и т.д.). Также в этой функции используется заранее заданная константа vbMonday.
Приведенная ниже формула возвращает 31/12/2001, что является первым понедельником после Рождества 2001 года (Рождество выпадает на вторник):
=NEXTMONDAY(DATE(2 0 01;12;2 5) )
Функция возвращает порядковый номер даты. Чтобы отобразить порядковый номер в виде действительной даты, нужно изменить формат номера в ячейке.
Если аргумент, обработанный функцией NEXTMONDAY, выступает понедельником, функция возвратит значение следующего понедельника. Чтобы функция возвратила значение этого понедельника, введите следующий код:
556 |
Часть VI. Разработка пользовательскихфунк |
Function NEXTMONDAY2(d As Date) As Date
1 |
Возвращение следующего понедельника илитекущей даты, если |
1 |
d равно aMonday |
If WeekDay(d) = 2 Then
NEXTMONDAY2 = d
Else
NEXTM0NDAY2 = d + 8 - WeekDay(d, vbMonday)
End If
End Function
Вычисление следующего дня недели
Следующая функция NEXTDAY является вариацией функции NEXTMONDAY. Эта функция принимает два аргумента: дату и целое число в диапазоне от 1 до 7,соответствующее дню недели (l=Sunday, 2=Monday и т.д.). Функция NEXTDAY возвращает дату следующегодня недели.
Function NEXTDAY(d As |
Date, day As Integer) |
As Variant |
|
' |
Возвращение следующего определенного дня |
недели |
|
1 |
Убедитесь что день |
задан в диапазоне 1-7 |
|
|
If day < 1 Or day |
> 7 Then |
|
NEXTDAY = CVErr(xlErrNA)
Else
NEXTDAY = d + 8 - WeekDay(d, day)
End If
End Function
В функции NEXTDAY используется оператор If, обеспечивающий приемлемость аргумента дня (принадлежит диапазону от 1 до7). Если аргумент дня является неприемлемым числом, функция возвращает значение #Н/Д. Поскольку функция может возвратить другое значение, ане дату, ее тип описан как v a r i a n t .
Неделя месяца
Приведенная ниже функция MONTHWEEK возвращает целое число, соответствующее номеру неделимесяца.
Function MONTHWEEK(d As Date) As Integer
'Возвращение недели месяца для указанной даты
Dim FirstDay As Integer
1 |
Проверка |
правильности аргумента |
|
If Not IsDate(d) Then |
|
|
MONTHWEEK = CVErr(xlErrNA) |
|
|
Exit |
Function |
|
End If |
|
1 |
Получение |
первого дня месяца |
|
FirstDay |
= WeekDay(DateSerial(Year(d), Month(d), 1)) |
1 |
Вычисление недели месяца |
|
|
MONTHWEEK |
= Application.RoundUp((FirstDay + day(d) - 1) / 7, 0) |
End |
Function |
|
Глава 25. Примеры пользовательских функций VBA |
557 |
Управление датами до1900 года
Многие пользователи удивляются, когда выясняется, что Excel не умеет работать с датами до 1900 года. Чтобы исправить этот недостаток, я создал надстройку, которая называется Extended Date Functions (Функции продолжения дат). Эта надстройка позволяет работать с датами начиная с 0100 года и заканчивая 9999 годом.
Установленная настройка Extended Date Functions дает возможность работать с восемью дополнительными функциямирабочего листа:
•XDATE(y,m,d,fmt). Возвращает дату определенного года, месяца и дня. В качестве параметра можно задать строку формата даты.
•XDATEADD(xdatel,days,fmt). Добавляет определенное число дней к дате. В качестве параметра можно задать строку формата даты.
•XDATEIF(xdatel,xdate2). Возвращает количество дней между двумя датами.
•XDATEYEARDIF(xdatel,xdate2). Возвращает количество полных лет между двумя датами (используется при вычислении возраста).
•XDATEYEAR(xdatel). Возвращает год указанной даты.
•XDATEMONTH(xdatel). Возвращает месяц указанной даты.
•XDATEDA Y(xdatel). Возвращает день указанной даты.
•XDATEDOW(xdatel). Возвращает день недели указанной даты (в виде целого числа от 1 до 7).
Функции не подстраиваются под изменения, вносимые в календарь в 1582 году. Поэтому результаты управления датами до 15 октября 1582 года могут быть неправильными.
Возвращение последней непустой ячейки столбца или строки
В этом разделе представлено две функции: LASTINCOLUMN, которая возвращает содержимое последней непустой ячейки в столбце, и LASTINROW, которая возвращает содержимое последней непустой ячейки в строке. В главе 13 описаны формулы массивов, используемые с той же целью, но длярешения этой задачи можно также использовать и пользовательские функции.
Каждая изэтих функций в качестве одного аргумента принимает диапазон. Аргументом может быть ссылка на столбец (для LASTINCOLUMN) или строку (для LASTINROW). Если принимаемый аргумент соответствует ссылке на неполную строку или столбец (например, 3 :3 или D:D), то в функции используется столбец илистрока левой верхней ячейки диапазона. Например, следующая формула возвращает содержимое последней непустой ячейки изстолбца В:
=LASTCOLUMN(B5)
А следующая формула возвращает содержимое последней непустой ячейки в строке 7: =LASTROW(C7:D9)
558 |
Часть VI. Разработка пользовательскихфунк |
Функция |
LASTINCOLUMN |
|
|||
|
Ниже приведена функция LASTINCOLUMN: |
|
|||
Function |
LASTINCOLUMN(rng As |
Range) |
|
||
1 |
Возвращение содержимого |
последней |
непустой ячейки столбца |
||
|
Application.Volatile |
|
|
||
|
With |
rng.Parent |
|
|
|
|
|
With |
.Cells(.Rows.Count, rng.Column) |
||
|
|
|
If Not IsEmpty(.Value) Then |
||
|
|
|
LASTINCOLUMN |
= .Value |
|
|
|
|
Elself IsEmpty(.End(xlUp)) |
Then |
|
|
|
|
LASTINCOLUMN |
= "" |
|
|
|
|
Else |
|
|
LASTINCOLUMN = .End(xlUp).Value End If
End With End With
End Function
Обратите внимание на ссылку Parent диапазона. Она позволяет функции работать с аргументами, которые ссылаются на различные рабочие листы и книги.
Функция LASTINROW
Следующая функция LASTINROW:
Function LASTINROW(rng As Range)
1 Возвращение содержимого последней непустой ячейки строки Application.Volatile
With rng.Parent
With .Cells(rng.Row, .Columns.Count)
If Not IsEmpty(.Value) Then
LASTINROW = .Value
Elself IsEmpty(.End(xlToLeft)) Then LASTINROW = M "
Else
LASTINROW = .End(xlToLeft).Value End If
End With End With
End Function
Функции для работы внескольких листах
Иногда нужно создать функцию для работы с данными, которые содержатся на нескольких рабочих листах одной рабочей книги. В этом разделе предлагается две функции VBA, которые позволяют работать с данными из различных листов, в том числе функции, которые обходят ограничения Excel на копирование формул в другой лист.
Глава 25. Примеры пользовательских функций VBA |
559 |