4
Условные операторы и циклы
В этой главе я расскажу вам про условные операторы и циклы. Они - главные части любой программы и являются определяющими элементами выполнения программы. Я начну с объяснения булевых значений и как PureBasic обрабатывает их и после этого перейду к условным операторам таким как, 'IF' и 'Select', которые используются, чтобы определить выполнение программы на основе различных условий. Закончу главу с объяснениями и примерами различных циклов, которые доступны для использования в PureBasic. Как всегда будут даны полные объяснения наряду с большим кол-вом примеров.
Булевая логика
Сначала давайте окунемся в историю. Джордж Буль был
математиком и философом, который изобрел форму алгебры, называющуюся
теперь булевой алгеброй. Логику этой формы алгебры назвали Булевой в
честь Джорджа Буля. Эта форма давно стала основой всех современных
компьютеров.
Что удивительно, так это то, что Джордж Буль изобрел эту форму примерно
семьдесят лет назад до создания первого компьютера, который начал
использовать его! По сути, вся система вращается вокруг двух значений,
TRUE(истина) и False(ложь). Эти два
значения, проверяются с помощью логических операций, для определения
результата. На самом деле это не так сложно. Три самые основные
логические операции были (и остаются) AND, OR и NOT. Именно эти три
оператора, легли в основу алгебры Буля, добавим операции, необходимые
для выполнения сравнений и элементарную математику. (В главе 3 подробно
рассказывается про эти логические операции). У PureBasic нет булевого
типа данных , в отличие от некоторых языков, такие как C++. Так в
PureBasic, чтобы выразить истину или ложь мы используем числа.
‘1’ истина и ‘0’ ложь, помните это! Поскольку мы
используем эти числовые значения для представления
TRUE(истина) и
FALSE(ложь), то
неплохо было бы использовать в PureBasic встроенные константы. Это
поможет сделать ваш программный код легко читаемым и понимаемым в
дальнейшем. Вот две константы:
#True
#False
# True имеет значение '1' и # False имеет значение '0'.
Почти все команды в PureBasic возвращают значение. Иногда это значение-математическая функция или это может быть состоянием окна, которое Вы только что создали. Эти значения возвращаются, чтобы иметь возможность проверить их при случае. Посмотрите пожалуйста на этот код(авторский код изменен на русский для большего понимания):
if Создано
окно True
тогда я размещу на нем мои
кнопки и графику
else
есть
какие то проблемы с созданием окна
end the program
Это не реальный компилируемый код, это только идея, в которой я пытаюсь объяснить суть логики. И так я спрашиваю:
Создано ли мое окно?
Если значение равно TRUE , тогда я могу разместить на моем окне мою графику и кнопки.
Если значение не равно TRUE, то есть оно равно FALSE, то вылетит сообщение что есть какие то проблемы.
Это первое впечатление о важности наличия истинных и ложных значений. А теперь пора в следующий раздел.
Оператор IF
Команда IF используется для
управления
потоками программы
на основе необходимой логики.Иногда, когда программа
еще не запущена, вы
можете получить неправильный запуск или ошибки и
неплохо было бы иметь возможность для обработки
таких вещей.
Конструкция оператора IF
Оператор используется для проверки на истинность значения. Если он получает значение TRUE(истина), то он сразу же выполняет кусок кода после первой строки: IF......... Если он не получит этого значения, он будет выполнять другой отдельный кусок кода сразу же после Else. Давайте посмотрим на примере:
a.l = 5
If
a = 5
Debug "A true value was found"
Else
Debug "No true value was found"
EndIf
Здесь оператор 'IF' тестирует равна ли переменная "а" числу "5". Он возвращает значение TRUE, поэтому выполняется код в сроке сразу после строки IF. Если бы это сравнение оказалось FALSE, то выполнился бы код сразу после строки с командой 'Else'. Чтобы определить конец работы для оператора IF, нужна команда ENDIF.
О значениях
В PureBasic ‘1’ =True и ‘0’ =False. Oператор 'IF' распознает эти два значения и использует в своей структуре в зависимости от логики.
Обратите внимание при изучении 'IF' : команда ENDIF обязательна при создании IF, другое дело команду ELSE можно использовать по надобности. Так например следующий пример покажет вам это:
a.l = 5
If a = 5
Debug "A true value was found"
EndIf
Единственный недостаток этого примера: нет команд при возврате оператором False . Вам конечно решать нужны ли команды при срабатывании False в вашем коде оператором. А мы попросту возьмем следующий пример, в котором задаем условия для оператора, определяющего: имеет ли переменная какое либо значение?
Beads.l = 5
If Beads
Debug "переменной присвоено значение"
Else
Debug "переменной не присвоено значение"
EndIf
Здесь оператор IF проверяет имеет ли переменная BEADS значение отличное от 0. В нашем примере переменная имеет значение и соответствующий кусок кода выполняется. Попробуйте изменить значение на 0 и запустить снова.
Давайте взглянем на более сложный пример с использованием оператора IF. Если вам сложны для понимания некоторые операторы, прочитайте главу 3.
Value1.l = 10
Value2.l = 5
Value3.l = 1
If
Value1 >= 10 And (Value2 / 5) =
Value3
Debug "The expression
evaluates as true"
Else
Debug "The expression
evaluates as false"
EndIf
Здесь мы проверяем: value1 больше или равно 10 а так же Value2 разделенное на 5 равно Value3. Как вы можете видеть: выражения проверяемые могут быть довольно сложными.
Команда ELSEIF
Другая команда, которая может быть использоваться в рамках оператора "IF", это команда ElseIf. Как следует из названия команды, она представляет собой сочетание Else и IF. Если оригинал IF оценивается как False, то проверяется кусок кода со строкой ElseIf. Однако, в отличие от Else, для того чтобы оценивать альтернативные условия, можно использовать несколько команд ElseIf. Я покажу пример с использованием одной команды ElseIf, но вам ничего не мешает попрактиковаться и добавить еще несколько условий с командами ElseIf:
NumberOfBeads.l = 10
If
NumberOfBeads < 5
Debug "The variable has a value below '5'"
ElseIf
NumberOfBeads > 5
Debug "The variable has a value above '5'"
Else
Debug "The variable has a value of '5'"
EndIf
Здесь мы проверяем значение переменной NumberOfBeads. В
первой строке проверки тестируется: является ли это значение меньше
"5". Поскольку возращается False, программа
переходит к части кода ElseIf. В строке ElseIf проверка
возвращает TRUE, потому что NumberOfBeads больше, чем "5". Значит кусок
кода со строкой ELSE
выполняться не будет.
Команда ElseIf по сути является отличным способом расширить
оператор IF, чтобы проверить
множество значений. Единственным недостатком является то, что когда
большое число этих команд используется, код станет слишком огромен.
Когда нужно проверить много значений, предпочтительней использовать
оператор SELECT
Немного обобщим:
IF...........
код
ELSEIF.........
код
ELSEIF.........
код
ELSE........
код
ENDIF
1)Проверяется строка IF
2) Если возратило False, то проверяем строки ELSEIF, пока не возратится TRUE
3) Если везде возратилось FALSE, то выполняем команду ELSE
4) Выходим из проверки командой ENDIF
Оператор SELECT
Оператор SELECT можно считать прямым дополнением к "IF". Он удобен только если необходимо проверить несколько условий . Позвольте мне показать вам пример правильного синтаксиса и объяснить его использование:
Days.l = 2
Select
Days
Case 0
Debug "0 Days"
Case 1
Debug "1 Day"
Case 2
Debug "2 Days"
Default
Debug "Over 2 Days"
EndSelect
Оператор начинается с команды SELECT, которой задается выражение или переменная для тестирования, в данном случае это переменная Days. Командам CASE задаются значения. Если какое нибудь значение равно переменной, то выполняется соответствующий код ниже команды Case, задающей это значение. В нашем примере переменная Days имеет значение 2. Сначала выполнится сравнение Case 0, потом Case 1, далее Case 2 и поскольку Days имеет значение 2, то выполнится код Debug "2 Days". И оператор SELECT закончит свою работу завершающей командой ENDSELECT. Вы заметили, что последней командой в сравнении стоит Default. Это кусок кода, который выполняется, если все другие CASE возвратят FALSE, своего рода как Else в рамках IF.
Проверка на наличие нескольких значений
SELECT можно использовать для проверки на множество разных значений и при этом код будет краток. Вот пример:
Weight.l = 12
Select
Weight
Case
0
Debug
"No Weight"
Case
1, 2, 3
Debug
"Light"
Case
4 To 15
Debug
"Medium"
Case
16 To 30
Debug
"Heavy"
Default
Debug
"Massive"
EndSelect
Здесь вы можете увидеть, что после команды CASE можно задавать несколько значений через запятую, и конечно если какое нибудь из этих значений будет равно тому, что задано в SELECT, выполнится соответствующий код ниже CASE. Кроме того вы наверно заметили, что после CASE, можно задавать интервал значений: 4 TO 15, то есть от 4 до 15. Интервал задается командой TO. А теперь еще один пример оператора SELECT в консольном приложении.
If OpenConsole()
PrintN("1. Official PureBasic Home")
PrintN("2. Official PureBasic Forums")
PrintN("3. PureArea.net")
PrintN("")
PrintN("Enter a number from 1 To 3 and press
Return: ")
Destination.s = Input()
Select Destination
Case "1"
RunProgram("http://www.purebasic.com")
Case "2"
RunProgram("http://forums.purebasic.com")
Case "3"
RunProgram("http://www.purearea.net")
EndSelect
EndIf
End
В этом примере я использовал несколько новых команд, с которыми вы не
знакомы, но я думаю, что это не так сложно для понимания. Программа
четко демонстрирует использование SELECT.
Новые команды будут объяснены попозже, но я думаю, можно понять, что
происходит, глядя на их описательные названия. По сути программа
ожидает от вас нажатия на клавиши 1 или 2 или 3, в зависимости от того
на какой сайт вам надо попасть, а оператор
SELECT обрабатывает ваш выбор и функция
RunProgram() запускает нужный сайт.В качестве примечания хотелось бы
сказать, что я использовал оператор
IF для проверки
возможности запуска консоли. Если функция OpenConsole () возвращает
TRUE, откроется окно консоли
и выполнится код внутри оператора IF-ENDIF.
Если функция вернет FALSE,приложение
просто завершится. Не печальтесь, если чего нибудь из прошлого примера
вы не поняли, со временем к вам придут знания и опыт.
Циклы
Чтобы иметь возможность непрерывно получать и обрабатывать данные, используют циклы. Во всех программах, которые используют GNU, используются циклы для управления и разработкой интерфейса, а так же для слежением за вводом от пользователя. Например, в IDE PureBasic используется очень много циклов, для контроля за нажатиями клавиш и кнопок мыши, для обновления дисплеев и т.д. Циклы также отличный способ обработки больших объемов данных, в том числе массивов или связанных списков.
Цикл FOR
Первый цикл, о котором я буду говорить, является вероятно самым известным и возможно наиболее используемый из всех циклов это FOR. Эти циклы, иногда называемые циклами FOR / NEXT, являются отличным способом выполнения обработки данных. Когда вы нуждаетесь в переменной приращения, то есть использовать ее как счетчик например для индекса массива . Вот пример простого цикла:
For x.l = 1 To 10
Debug x
Next x
В этом примере мы создали цикл, используя команду
FOR. Переменная Х
с типом long будет началом нашего
цикла и мы присвоили этой переменной "1", а следовательно и старт нашего цикла будет с
числа "1". Далее
вводится диапазон командой TO, верхним
пределом которого я установил ‘10’ , это число будет концом
нашего цикла. Последней строчкой нашего кода, мы устанавливаем
команду NEXT(СЛЕДУЮЩИЙ),
все с той же переменной Х. Эта команда будет увеличивать цикл на
единицу. Когда переменная достигнет большего числа ,чем то что
заложено верхним пределом то есть больше десяти "10", цикл завершит
свою работу. Ну и для наглядности, внутрь цикла мы запехнули команду Debug X,
которая выводит результат работы цикла в отладочное окно.Может
не совсем понятно? Попробую разжевать: И так цикл- это петля. Все что
лежит внутри цикла, выполняется столько раз, сколько мы заложим в
строчке с командой
FOR. В нашем случае 10. А теперь поменяйте
строчку кода x.l = 1 To 10 вот
на такую x.l = 5 To 11 и
посчитайте сколько результатов в отладочном окне.Думаю теперь понятно.
Вот другой пример использования цикла, для легкого перечисления массива:
Dim Names.s(3)
Names(0) = "Gary"
Names(1) = "Sara"
Names(2) = "Stella"
Names(3) = "MiniMunch"
For x.l = 0 To 3
Debug Names(x)
Next x
Все значения массива доступны с использованием
индексов, и эти показатели всегда начинаются с нуля. Циклы FOR легко использовать с массивами, это дает нам
небольшой код по размеру, независимо от того, какой размер массива.
Больший массив просто потребует больший диапазон в первой строке цикла FOR
Циклы FOR могут быть построены
так же с использованием выражений:
StartVar.l = 5
StopVar.l = 10
For x = StartVar - 4 To StopVar / 2
Debug x
Next x
и, конечно, циклы могут быть вложенными, если вам нужно обработать многомерные массивы:
Dim Numbers.l(2, 2)
Numbers(0, 0) = 1
Numbers(0, 1) = 2
Numbers(0, 2) = 3
Numbers(1, 0) = 4
Numbers(1, 1) = 5
Numbers(1, 2) = 6
Numbers(2, 0) = 7
Numbers(2, 1) = 8
Numbers(2, 2) = 9
For x = 0 To 2
For y = 0 To 2
Debug Numbers(x, y)
Next y
Next x
В прошлом примере получился цикл в цикле. Чтобы вам было проще понять поясню на примере часов: представьте себе что, большой цикл это часовая стрелка, а маленький цикл это минутная стрелка помотрим сколько движений пройдет минутная стрелка(это будет у нас Z) за два часа (X):
z=1
For x=1 To 2
For y=1 To 60
Debug z
z=z+1
Next y
Next x
То есть за одно прохождение большого цикла, маленький цикл пройдет 60 раз.А поскольку в нашем примере диапазон большого цикла равен 2, то маленький цикл пройдет два раза по 60, то есть 120. Данный пример обязательно загрузите, если что то непонятно с циклами.
Вы можете сделать столько циклов сколько пожелаете без всяких ограничений. До сих пор вы видели, что нарастание цикла было на 1, но мы можем это изменить по своему желанию с помощью команды STEP (шаг):
For x.l = 0 To 10 Step 2
Debug x
Next x
Обратите внимание на команду STEP, ее мы записываем в той же строчке что и FOR. Команда STEP указывает нам в данном примере, что счетчик должен увеличиваться на 2 при каждом прохождении цикла.Если вы запустите этот пример и посмотрите в окно отладки, вы увидите значения, кратные 2.
Цикл ForEach
Этот вид цикла отличается от всех других тем, что он работает только со связанными списками. Синтаксис очень похожий на "FOR" за исключением того, что не требуется указывать диапазон, достаточно указать имя списка. Вот простой пример:
NewList Shopping.s()
AddElement(Shopping())
Shopping() = "Bunch of bananas"
AddElement(Shopping())
Shopping() = "Tea bags"
AddElement(Shopping())
Shopping() = "Cheese"
ForEach Shopping()
Debug Shopping()
Next
В этом примере определен связанный список и добавлено несколько элементов. Я использую цикл ForEach к этому списку и все его содержимое вывожу в окно вывода отладки. Как вы можете видеть, синтаксис очень простой. Цикл начинается с команды ForEach , за которым идет название списка. Конец цикла определяется с помощью команды Next . Код, который находится между этими двумя командами выполняется, пока цикл не дойдет до конца связанного списка. Далее цикл завершит работу. Цикл ForEach работает для всех типов связанных списков, в том числе и для структурированных связанных списков. Об этом больше будет рассказано в главе 5.
Цикл While
Этот цикл довольно удобный для определенных целей. Команда While задает начало цикла. В этой же строчке задается условие при котором цикл готов работать и выполняться до тех пор, пока это условие истинно. Команда Wend показывает конец петли цикла. То есть все, что находится между командами While - Wend будет выполняться до тех пор, пока выполняется условие, записанное в строке вместе со строкой While. Вот пример:
Monkeys.l = 0
While Monkeys < 10
Debug Monkeys
Monkeys + 1
Wend
Этот цикл будет выполняться до тех пор, пока переменная Monkeys будет меньше 10. Сначала эта переменная равна 0. При Каждом прохождении цикла Monkeys увеличивается на единицу, то есть как только Monkeys достигнет 10, цикл прервется. Запустите данный код и будет все понятно.А теперь пример цикла который не будет работать, поскольку условие не соответствует:
Monkeys.l = 20
While Monkeys < 10
Debug "This code is never executed"
Wend
Цикл Repeat
Такие циклы почти противоположны циклам While. Цикл начинается с Repeat и заканчивается одним из двух способов. Первый способ заключается в использовании условного выражения Until, а второй способ использует безусловное выражение Forever. Я полностью объясню оба направления , начиная с Repeat-Until:
Bananas.l = 0
Repeat
Debug Bananas
Bananas + 1
Until Bananas > 10
В отличии от цикла While, цикл
Repeat будет выполняться пока условие
записанное в строке Until не станет
истинным. То есть пока условие не выполняется, цикл
будет работать. Кроме того циклы Repeat, вне зависимости от условий, выполняются хотя бы
один раз.Вот пример:
Bananas.l = 20
Repeat
Debug Bananas
Until Bananas > 10
Кол-во Bananas = 20 и это совпадает с условием, записанным в строке с командой Until. Значит, как только цикл пройдет один раз, он завершится.Далее пример бесконечного цикла, но прежде чем запустить его: ВНИМАНИЕ! Зайдите в меню Меню Debugger, там есть строка меню Kill Program. Это команда - закилять программу вне зависимости от выполнения. Поскольку как только вы включите бесконечный цикл, выйти из него сможете только закиляв программу, либо выключив системными средствами. Ну ладно теперь пример:
Counter.l = 0
Repeat
Debug Counter
Counter + 1
ForEver
Ручная остановка циклов
Иногда,
когда вы используете циклы в вашей программе вы можете столкнуться с
проблемой непреднамеренными непрерывными циклами. Это может вызвать
проблемы в ваших программах, поскольку эти петли могут остановить всю
остальную работу до их выхода.В PureBasic IDE делается это легко. Если
вам нужно остановить запущенные программы вручную, то просто нажмите
Kill Program на панели инструментов
IDE, это тот, который выглядит как череп (в PureBasic 4.40, значок
черепа, был заменён на красный крестик) или используйте команду
меню Debugger-> Kill
Program. Это не только остановит
цикл, но и сделает выход из всей программы.
Управление циклами используя Break и Continue
В любое время все эти различные типы циклов могут
управляться двумя командами: Break и Continue.Я объясню комаанду
Break в первую очередь.
Если команда Break используется в любом
месте любого типа циклов, то цикл завершает работу как только
столкнется с этой командой. В случае вложенных циклов, есть
необязательный параметр, который может быть добавлен к команде Break,
который указывает, скольким циклам завершиться. А теперь пример команды
Break:
For x = 1 To 10
If x = 5
Break
EndIf
Debug x
Next x
В данном примере цикл прервался, как только сработало условие х=5. А теперь пример вложенных циклов с командой Break и с необязательным параметром для нее:
For x.l = 1 To 10
Counter = 0
Repeat
If x = 5
Break 2
EndIf
Counter + 1
Until Counter > 1
Debug x
Next
Как только х будет равен 5, завершатся оба цикла, поскольку параметр Break равен 2.
Далее будем рассматривать команду Continue.
Она позволяет в любой момент выпрыгнуть из
текущей итерации(значению петли) и
перейти к следующей в
текущем цикле. Это более просто, чем кажется:
For x.l = 1 To 10
If x = 5
Continue
EndIf
Debug x
Next
Здесь вы можете увидеть, что когда X равно 5, команда
Continue прерывает пятую итерацию и продолжает сверху в начале шестого
итерации, где X станет равно 6. Из-за этого прыжка можно заметить, в
окне отладки число 5 не отображается.
Циклы могут быть использованы для различных целей в программировании. В
первую очередь для сокращения утомительного кода и для перебора
огромных объемов данных. Надеюсь, теперь вы поняли, как можно их
использовать.
Я(Станислав Будинов) не
удостоверяю, что перевод дословный и 100% правильный. Более того многое
я вырезал, некоторое добавил.Но в основном я старался идти в ногу с
автором.