Visual2000 · Архив статей А.Колесова & О.Павловой
Андрей Колесов
© 1996, Андрей КолесовПри освоении системы программирования, тем более новой, нужна хорошая литература. Безусловно, помогает документация и встроенная справочная система, но этого явно недостаточно для нормальной работы. Во-первых, я абсолютно уверен, что у большинства пользователей VB в России документации просто нет. (Рекламная пауза: "Покупайте лицензионные продукты.") Во- вторых, назвать ее исчерпывающей и до конца понятной — никак нельзя. Здесь лучше всего вспомнить о том, что Коран — одна книга, а толкования к нему насчитывают тысячи томов. И в- третьих, оказывается, что довольно большое число отечественных программистов предпочитают описания на русском языке.
В начале марта в продаже появилась новая книга на тему VB: "Visual Basic 3.0, Visual Basic 4.0 для Windows" (Москва, ABF, 1996, 360 стр., тираж 11 тыс. экз.) Имя ее автора, Хачатура Арушанова, хорошо известно в среде российских VB-программистов по публикациям в прессе и активной деятельности в сети FIDO. Книга предназначена в первую очередь для начинающих VB- программистов. Основная ее часть — систематический справочник по языку (описание операторов), и в этом плане она очень хорошо дополняет книгу "Running Visual Basic 3 for Windows", о которой я упоминал в Совете 4. Вообще я должен сказать, что написание книги о VB является делом непростым. Здесь важно определить точку отсчета — базовые знания языка читателя. Для меня, как человека, имеющего опыт программирования в QuickBasic, операторы VB процентов на 80 давно известны, и мне интереснее прочитать о свойствах, методах и пр. Однако многие VB-программисты незнакомы с базовым языком.
Книга Арушанова, кроме справочника, содержит и другие интересные сведения, советы и пр. В общем — книга полезная, и здесь мое мнение совпадает с мнением многих моих знакомых, прочитавших ее. Но все же надо сказать, что вторая часть заголовка "... Visual Basic 4.0" не должна вводить в заблуждение читателя — в статьях самого Арушанова, опубликованных ранее в "ComputerWeek", говорится о VB 4.0 гораздо подробнее. Впрочем, это не должно расцениваться как упрек автору: VB 4.0 — это целый мир, охватить который в одной книге просто невозможно.
В связи с этим следует упомянуть, что в США в продаже постоянно имеется несколько десятков книг, освещающих самые различные аспекты программирования на VB (базы данных, мультимедиа, классы, объекты и пр). Как правило, они имеют объем от 500 до 1200 стр., включают дискету или CD-ROM с программными примерами и стоят от 30 до 45 долл. В каждом номере американского журнала VBPJ в специальном разделе публикуются аннотации этих книг. В конце прошлого года, в связи с выходом VB 4.0, появилось огромное количество книг, посвященных этой версии. Среди них есть и переиздания, и принципиально новые книги, число которых продолжает расти. Я привожу здесь информацию об американских изданиях не с целью подразнить российских пользователей "их" жизнью, а для того, чтобы сказать, что при желании все эти книги можно реально приобрести. Готов поделиться собственным опытом.
Наличие оператора Option Explicit (он находится в части Declarations программного модуля) свидетельствует о том, что все переменные данного модуля должны быть объявлены с помощью операторов DIM или REDIM. При появлении необъявленных переменных выдается сообщение об ошибке при запуске программы.
Для управления автоматической установкой этого режима во всех создаваемых модулях и формах установите флажок Reqiure Variable Declaration в положение Yes/No. Это флажок находится в диалоговом окне Environment Options, обращение к которому выполняется через соответствующую команду в меню Tools (VB 4.0) или Options (VB 3.0).
Отношение программистов к необходимости этого оператора непосредственно зависит от их квалификации. В частности, большинство профессионалов считают, что такой функции вообще не должно быть, так как явное описание переменных должно быть обязательным всегда. По их мнению, отсутствие ранее подобного режима — один из явных признаков "примитивности" Basic.
Традиционно Basic (и не только он, но и, например, Fortran) использовал принцип "по умолчанию". Его смысл заключался в том, что первое появление названия переменной в тексте программы автоматически означало ее объявление — самого существования переменной и ее типа. Вроде бы, это облегчало жизнь программистам (не надо было писать одну-две строки в заголовке модуля), но проблемы, возникающие при отладке из-за неправильного написания имен переменных, могли быть весьма значительными. Приведем примеры таких ситуаций.
i% = 1: m = I
Здесь программист забыл поставить в идентификаторе знак "%", в результате появилась новая переменная i, а значение m стало равным 0, а не 1.
MainCount = 1: m = MaimCount
То же самое — ошибка в написании идентификатора из-за довольно сложного имени (бывает и сложнее).
Обнаружить такие ошибки в больших программах бывает непросто. Этих проблем не возникло бы, если бы был установлен режим Option Explicit и эти переменные были бы объявлены:
Dim i%, MainCount
Явное описание переменных является хорошим поводом подумать об оптимальном использовании переменных в программе. Еще один пример:
For i = 1 To 10 ... If A > B Then i = 1 Else i= 2 Next
В данном случае программист забыл, что переменная i является счетчиком цикла, и задействовал ее в качестве флажка. В классическом варианте описание переменной должно было выглядеть так:
Dim i ' i - счетчик цикла
Такое описание подсказало бы программисту, что переменная i уже использована в других целях.
Смысл этого простого совета заключается в следующем. Время выполнения операций для числовых данных разных типов различается довольно значительно. Кроме того, для их хранения требуются различные размеры памяти. Поэтому следует выбирать оптимальный тип переменной в зависимости от ее применения. Это особенно актуально для больших программ, но привыкать к этому нужно сразу. Не забывайте, например, что переменные Integer всегда работают значительно быстрее, чем Single и Variant.
В связи с этим следует напомнить, что в VB имеются три варианта определения типа переменной:
Dim Variable[суффикс - %,#,!,&,$,@] Dim Variable As .... Dim Variable
Современный стиль программирования предполагает использование смысловых идентификаторов (например, "FileNumber", а не "Ifn"), поэтому такой способ определения типа переменной применяется все реже. Тем не менее он очень удобен для новой установки по умолчанию всех переменных модуля. Чаще всего это делается для установки целочисленного типа: Defint I-Z.
Собственно это продолжение предыдущего совета.
Сначала некоторые общие соображения. Учитывая, что создание программы должно укладываться в определенные сроки, общая стратегия разработки строится следующим образом. Прежде всего как можно быстрее создается первый работающий вариант, а затем выполняется доводка, в первую очередь фрагментов программы, наиболее критичных с точки зрения быстродействия. Здесь достаточно четко действует известный закон статистики 20/80 ("20% населения выпивают 80% пива") — "20% программы занимают 80% времени ее выполнения" и соответственно "20% программы требуют 80% времени на их разработку". При этом, разумеется, не стоит пренебрегать "правилами хорошего тона" и в процессе написания первого варианта программы. В связи с этим очевидный совет: будьте особенно внимательны при написании больших циклов.
Рекомендации, касающиеся кода, связанного с обработкой числовых данных, хорошо известны:
Что касается строковых переменных, что специфика работы с ними заключается в том, что они являются динамическими, поэтому самая длинная операция с ними — это простое присвоение: A$=... В этом случае каждый раз идет обращение к внутреннему диспетчеру динамической памяти, который фактически формирует новую переменную. Поэтому основной совет при работе со строками заключается в следующем: избегайте операций присвоения.
Как это сделать?
Довольно часто встречающейся программной конструкцией является формирование строковой переменной известной длины. Например, нужно сформировать строку, каждый байт которой равен его номеру в строке. Здесь можно использовать такие решения:
Вариант 1:
a$ = "": For n% = 1 To 255: a$ = a$ + Chr$(n%): Next
Вариант 2:
a$ = Space$(255): For n% = 1 To 255: Mid$(a$,n%) = Chr$(n%): Next
Второй вариант подлиннее, но будет работать существенно быстрее. Такой способ можно использовать и для случая, когда длина строки до начала цикла ее формирования неизвестна — сначала резервируется строка заведомо большей длины, а после окончания цикла выделяется нужное количество символов оператором LEFT$.
О пользе комментариев можно говорить много. В данном случае просто имейте в виду: комментарии не включается в состав исполняемого модуля и не влияют на его размеры и скорость выполнения.
Существует простой способ копирования сходных структур меню в несколько разных форм. Если сохранить файл как текст, тогда его секцию меню можно будет легко вставить в секцию меню нового файла с помощью любого текстового редактора.
Во многих случаях бывает необходимо выделить или подсветить целиком весь текст поля, когда на него устанавливается фокус. Тогда пользователь может просто начать ввод текста, чтобы заменить исходный текст на новый, или нажать клавишу Tab, чтобы оставить его как есть и перейти к следующему полю. Для выполнения этого требуется написать совсем немного кода. В общем модуле напишите следующий код:
Sub SetSelected() Screen.ActiveControl.SelStart = 0 Screen.ActiveControl.SelLength = _ Len(Screen.ActiveControl.Text) End Sub
А для каждого текстового поля включите такой текст:
Sub txtField_GotFocus() SetSelected End Sub
Текстовые окна в Windows всегда работают в режиме вставки и не обеспечивают возможность работы в режиме замены. Однако последний можно легко эмулировать, как показано здесь:
Sub Text1_KeyPress(KeyAscii As Integer) If KeyAscii >= 32 Then If Text1.SelLength = 0 Then If Text1.SelStart < Len(Text1) Then Text1.SelLength = 1 End If End If End If End Sub
Если вводится какой-либо символ (при условии, что текст не был выделен), данный код выбирает текущий символ, устанавливая свойство SelLength равным 1, и позволяет тем самым заменить его вводимым символом.
Для этого нужно установить свойство TabStop = False для всех элементов управления в активной форме. После этого вы сможете вводить символы "tab" (chr 9) в текстовые поля элементов управления. Если нужно, чтобы клавиша Tab "вела себя обычным образом" (то есть осуществляла переход к следующему элементу управления) для одного из элементов управления такой формы, то достаточно просто эмулировать ее работу с помощью следующего кода:
Sub Command2_KeyDown (KeyCode As Integer, _ Shift As Integer) ' На примере 3-х командных кнопок If KeyCode = 9 Then If Shift = 0 Then Command1.SetFocus ' Tab - следующий элемент управления ElseIf Shift = 1 Then Command3.SetFocus ' Shift+Tab - предыдущий End If End If End Sub