Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

Lab03_2010

.pdf
Скачиваний:
29
Добавлен:
07.06.2015
Размер:
1.72 Mб
Скачать

Рис. 20 Подключение папки с Javadoc

Рис. 21. Включение окна Javadoc c краткими сведениями о классе

11

Окно появится в нижней части окна среды, там же, где вкладка Output, в которой Вы вводили данные и видели получаемые результаты при работе приложения под управлением среды. Установите текстовый курсор (щелкните в этом месте кода мышкой), например, на Scanner, и в окне Javadoc Вы увидите описание класса (только общие сведения, без характеристик полей и методов) (рис. 22).

Рис. 22. Краткая информация о классе Scanner

Рис. 23. Полная страница Javadoc

12

Если же нужна более полная информация, в том числе о полях и методах класса, следует нажать Shift + F1. Тогда в главном окне среды появится дополнительная вкладка, на которой будет отображаться полная страница из Javadoc (рис. 23).

Если теперь посмотреть на сведения Javadoc для класса FileNotFoundException, то можно увидеть, что он является непосредственным наследником класса IOException (рис. 24).

Рис. 24. Класс FileNotFoundException наследует IOException

Поэтому его можно удалить из предложения throws, а также удалить соответствующее ему предложение импорта. Правда, сделать это придется вручную, поскольку такая операция с точки зрения инструмента Refactor, небезопасна (конечно, можно оставить все, как есть). В итоге конструктор класса Matrix будет записан следующим образом (рис. 25):

Рис. 25. Окончательный вид конструктора Matrix()

13

Итак, мы можем сформулировать «алгоритм» – как организовать чтение из (текстового) файла.

1)импортировать классы: java.io.FileReader (чтобы создать объект класса FileReader из текстового файла), java.io.IOException (поскольку придется обрабатывать или пропускать исключения, могущие возникнуть при работе с файлами), java.util.Scanner (чтобы использовать класс Scanner для чтения из объекта класса FileReader числовых или символьных данных).

2)разрешить пропускать ошибки ввода / вывода методу (методам), прямо или косвенно использующим объект класса FileReader, дописав к его (их) заголовку (- ам) (после списка параметров) предложение throws IOException

3)создать объект типа FileReader, передав в его конструктор в качестве параметра имя (текстового) файла

4)при создании объекта типа Scanner в качестве параметра в его конструктор передать объект типа FileReader

5)организовать чтение из файла, при необходимости установив нужную локаль.

6)по завершении работы закрыть объект типа FileReader методом close().

Сразу оговоримся, что этот «алгоритм» не претендует ни на общность, ни на единственность. Но для задач этой лабораторной работы он подходит.

§ 3. Просмотр результатов ввода с помощью отладчика

Чтобы проверить написанный нами конструктор «в работе», необходимо вызвать его в методе main() главного класса (рис .26):

Рис. 26. Создание объекта класса Matrix()

Сохраните и запустите проект. Если Вы все сделали верно, то единственным сообщением будет вывод об успешном построении проекта (рис. 27):

Рис. 27. Приложение успешно завершило свою работу

14

Разумеется, это не слишком наглядно показывает, что произошло при вводе. Отсутствие ошибок при компиляции и выполнении еще не свидетельство того, что все работает правильно. Конечно, можно организовать отладочный вывод – например, распечатать массив по завершении ввода. В простых случаях, возможно, это эффективный подход. Но современные среды программирования предоставляют инструменты, позволяющие отслеживать, что происходит во время выполнения программы. Эти инструменты достаточно разнообразны и мощны, пока мы познакомимся только с основными их возможностями.

Как правило, нет необходимости просматривать программу в ручном режиме целиком: обычно интересует выполнение какого-либо фрагмента кода. В начале интересующего фрагмента (или фрагментов) можно поставить так называемую точку останова. В режиме отладки программа будет выполнена автоматически до этого места в коде, после чего программист сможет действовать дальше на свое усмотрение.

Чтобы поставить точку останова, достаточно щелкнуть по номеру соответствующей строки в главном окне среды (если номера не отображаются, просто щелкнуть в этой области рядом со строкой). Эта строка будет подсвечена красным. Снять точку останова можно повторным щелчком. Поставьте точку останова на вызове конструктора Matrix() в методе main() (рис. 28):

Рис. 28. Точка останова

Теперь следует запустить приложение в режиме отладки. Это можно сделать с помощью меню Debug | Debug Main Project, клавиатурной комбинации Ctrl + F5 или же соответствующей кнопки на панели инструментов (рис. 29):

Рис. 29. Запуск приложения в режиме отладки

В главном окне среды строчка, на которой (автоматическое) выполнение остановилось, будет подсвечена зеленым. Кроме того, появятся две дополнительных вкладки в нижней части среды: Variables (именно она и откроется) и Breakpoints (рис. 30).

15

Рис. 30. Начиная с этой строчки, программист может действовать в «ручном» режиме

Вкладка Variables отображает переменные, актуальные в текущем контексте. Однако таковых, по сути, еще не существует: переменная mt пока не создана. Вкладка Breakpoints показывает список точек останова в программе. Если Вы переключитесь на эту вкладку, увидите информацию о той единственной точке останова, которая была поставлена на строке 23 (рис. 31):

Рис. 31. Во вкладке BreakPoints показаны точки останова

Рис. 32. Возможные шаги при отладке

Наблюдать за происходящим при отладке мы будем с помощью вкладки Variables, поэтому, если Вы переключались на вкладку Breakpoints, переключитесь вновь на Variables.

Обратимся вновь к меню Debug (рис. 32). Существует несколько возможностей сделать очередной шаг при отладке, которые сосредоточены в третьей секции этого меню. Мы кратко опишем некоторые из них:

Step Over (F8) – не «входить» в метод при его вызове (исполнять метод как «одношаговую операцию»)

Step Into (F7) – «входить» в метод при его вызове (перейти к исполнению кода метода в пошаговом режиме)

Step Out (Ctrl+F7) – «вернуться» из текущего исполняемого метода на уровень метода, его вызвавшего

16

— Run to Cursor (F4) – исполнить код в автоматическом режиме до позиции курсора (на рисунке этот пункт неактивен).

Еще один важный пункт меню – Continue (F5) – служит для перехода к следующей точке останова. Поскольку у нас пока лишь одна точка останова, изучение его работы мы отложим.

Нас интересует, как работает только что написанный конструктор класса Matrix, поэтому выполним Step Into (или нажмем F7). Зеленая строчка «исполнения» перейдет на заголовок конструктора (рис. 33):

Рис. 33. Вход отладчика в конструктор Matrix()

Обратите внимание, что теперь во вкладке Variables отображается единственная переменная this типа Matrix. Стоящий возле нее знак «+» свидетельствует о наличии внутренней структуры: нажав на него (после чего он превратится в «–»), Вы увидите поля

(рис. 34).

Рис. 34. Поля вновь создаваемого объекта пока пусты

Чтобы перейти к следующей исполняемой строчке, выполним Step Over (или нажмем F8), и зеленая строка сместится еще на одну линию ниже. Разумеется, если бы вместо вызова конструктора FileReader() в тексте программы находился бы вызов метода, разработанного нами самостоятельно и в работе которого мы не были бы уверены, можно

17

было бы нажать F7 (Step Into), чтобы просмотреть, как он работает. В нашем же случае это излишне. Впрочем, если Вы хотите посмотреть, как написан и работает конструктор FileReader(), Вы можете выполнить вход Step Into. В этом случае в главном окне среды откроется вкладка FileReader.java, а курсор отладки (зеленая строчка) переместится на первую строчку внутри конструктора класса FileReader (рис. 35).

Рис. 35. Можно исследовать работу класса FileReader

Выполняя Step Into, Вы, возможно, доберетесь даже до методов класса, лежащего в самом основании всей иерархии классов Java – класса Object. Однако если пока это исследование не представляется Вам интересным, выполните Step Out (Ctrl + F7), чтобы вернуться к исполнению конструктора класса Matrix (вкладка FileReader.java автоматически при этом не закроется, придется сделать это вручную). После того, как Вы выполните отладочный шаг (Step Over, F8) и с конструктором класса Scanner, обратите внимание, что во вкладке Variables появились новые переменные: fin и scr (рис. 36). Это локальные переменые, они существуют только внутри конструктора.

Рис. 36. После создания переменные fin и scr также отобразятся во вкладке Variables

Теперь, нажимая F8, Вы можете следить, как переменные n, m, а затем и array приобретают свои значения (рис. 37). Обратите внимание, что тип у поля array появится

18

только тогда, когда под него фактически будет выделена память. Тогда же и пустая ссылка null будет заменена некоторым адресом в памяти. Кроме того, у массива array будет также указана длина. Массивы с количеством измерений более одного трактуются как массивы массивов. Поэтому под длиной такого массива понимается количество элементов в его «первом» измерении (в нашем случае это 5 строк).

Рис. 37. Выделена память под массив

Нажав на знак «+» возле переменной array можно увидеть, что она состоит из пяти одномерных массивов (рис. 38).

Рис. 38. Элементами двумерного массива являются одномерные

Теперь, если «раскрыть», например, нулевую строчку массива, можно будет пронаблюдать ее заполнение в цикле for (по-прежнему нажимая F8). На рис. 39 приведен снимок экрана после выполнения трех итераций цикла for.

Заметьте, что по мере входа в циклы for (сначала во внешний цикл по i, затем во внутренний цикл по j) во вкладке Variables появились переменные i и j.

Нажимайте F8 и следите за происходящим с окном Variables по крайней мере до тех пор, пока не перейдете к заполнению третьей строки. Удостоверьтесь, что при чтении чисел из файла никакие элементы не пропускаются и что массив заполняется правильно.

19

Разумеется, когда заполнится нулевая строка, следует «свернуть» ее, нажав на «–», и «раскрыть» первую; после заполнения первой – «свернуть» ее и «раскрыть» вторую и т.д.

Рис. 39. Пошаговое заполнение массива array

Отслеживание заполнения массива, конечно, довольно увлекательный процесс, но далеко не всегда требуется проделывать это до конца. Нередка ситуация, когда в процессе исполнения какого-то фрагмента программы стало понятно, что именно он работает верно (или же, напротив, была обнаружена ошибка). После этого можно перейти к исполнению следующего фрагмента программы, причем начало этого фрагмента программы совершенно не обязательно является следующей точкой останова. В этом случае нам поможет шаг Run To Cursor. Установите курсор (щелкните мышкой) на строке с вызовом метода fin.close() и нажмите F4 (или же выполните пункт меню Debug | Run To Cursor).

Рис. 40. Шаг Run To Cursor приводит к выполнению всех операций до новой позиции курсора

20

Соседние файлы в предмете Программирование на Java