Главная страница
Навигация по странице:

  • Рис. 14.6.

  • Книга Изучаем Python


    Скачать 4.68 Mb.
    НазваниеКнига Изучаем Python
    Дата10.12.2022
    Размер4.68 Mb.
    Формат файлаpdf
    Имя файлаErik_Metiz_Izuchaem_Python_Programmirovanie_igr_vizualizatsia_da.pdf
    ТипКнига
    #837531
    страница35 из 53
    1   ...   31   32   33   34   35   36   37   38   ...   53

    ПРИМЕЧАНИЕ
    В некоторых классических играх выводимая информация снабжается текстовыми метками: «Уро- вень», «Рекорд» и т . д . Мы эти метки опустили, потому что смысл каждого числа понятен каждому, кто сыграл в Alien Invasion . Если вы включите эти метки, добавьте их в строки непосредственно перед вызовами font .render() в Scoreboard .

    Подсчет очков 303
    Рис. 14.5. Текущий уровень выводится под текущим счетом
    Вывод количества кораблей
    Остается вывести количество кораблей, оставшихся у игрока, но на этот раз инфор- мация будет выводиться в графическом виде. Как во многих классических аркад- ных играх, в левом верхнем углу экрана программа рисует несколько изображений корабля. Каждый корабль обозначает одну оставшуюся попытку.
    Для начала нужно сделать так, чтобы класс
    Ship наследовал от
    Sprite
    , — это не- обходимо для создания группы кораблей:
    ship.py
    import pygame from pygame.sprite import Sprite
     class Ship(Sprite):
    def __init__(self, ai_settings, screen):
    """Инициализирует корабль и задает его начальную позицию."""
     super(Ship, self).__init__()
    Здесь мы импортируем
    Sprite
    , объявляем о наследовании
    Ship от
    Sprite
     и вы- зываем super()
    в начале
    __init__()
    .
    Далее необходимо изменить
    Scoreboard и создать группу кораблей для вывода на экран. Команды import и метод
    __init__()
    выглядят так:
    scoreboard.py
    import pygame.font from pygame.sprite import Group

    304 Глава 14 • Ведение счета from ship import Ship class Scoreboard():
    """Класс для вывода игровой информации."""
    def __init__(self, ai_settings, screen, stats):
    self.prep_level()
    self.prep_ships()
    Так как мы собираемся создать группу кораблей, программа импортирует классы
    Group и
    Ship
    . Метод prep_ships()
    будет вызываться после prep_level()
    . Он вы- глядит так:
    scoreboard.py
    def prep_ships(self):
    """Сообщает количество оставшихся кораблей."""
     self.ships = Group()
     for ship_number in range(self.stats.ships_left):
    ship = Ship(self.ai_settings, self.screen)
     ship.rect.x = 10 + ship_number * ship.rect.width
     ship.rect.y = 10
     self.ships.add(ship)
    Метод prep_ships()
    создает пустую группу self.ships для хранения экземпляров кораблей . В ходе заполнения этой группы цикл выполняется по одному разу для каждого корабля, оставшегося у игрока . В цикле создается новый корабль, а координата x этого корабля задается так, чтобы корабли размещались рядом друг с другом, разделенные интервалами величиной 10 пикселов . Координата y за- дается так, чтобы корабли были смещены на 10 пикселов от верхнего края экрана и были выровнены по изображению текущего счета . Наконец, каждый корабль добавляется в группу ships
    .
    Следующим шагом становится вывод кораблей на экран:
    scoreboard.py
    def show_score(self):
    self.screen.blit(self.level_image, self.level_rect)
    # Вывод кораблей.
    self.ships.draw(self.screen)
    При выводе кораблей на экран мы вызываем метод draw()
    для группы, а Pygame рисует каждый отдельный корабль.
    Чтобы игрок видел, сколько попыток у него в начале игры, мы вызываем prep_
    ships()
    при запуске новой игры. Это происходит в функции check_play_button()
    из файла game_functions .py
    :
    game_functions.py
    def check_play_button(ai_settings, screen, stats, sb, play_button, ship,

    Подсчет очков 305
    aliens, bullets, mouse_x, mouse_y):
    """Запускает новую игру при нажатии кнопки Play."""
    button_clicked = play_button.rect.collidepoint(mouse_x, mouse_y)
    if button_clicked and not stats.game_active:
    # Сброс изображений счетов и уровня.
    sb.prep_score()
    sb.prep_high_score()
    sb.prep_level()
    sb.prep_ships()
    Метод prep_ships()
    также вызывается при столкновении пришельца с кораблем, чтобы изображение обновлялось при потере корабля:
    game_functions.py
     def update_aliens(ai_settings, screen, stats, sb, ship, aliens, bullets):
    # Проверка коллизий "пришелец-корабль".
    if pygame.sprite.spritecollideany(ship, aliens):
     ship_hit(ai_settings, screen, stats, sb, ship, aliens, bullets)
    # Проверяет, добрались ли пришельцы до нижнего края экрана.
     check_aliens_bottom(ai_settings, screen, stats, sb, ship, aliens, bullets)
     def ship_hit(ai_settings, screen, stats, sb, ship, aliens, bullets):
    """Обрабатывает столкновение корабля с пришельцем."""
    if stats.ships_left > 0:
    # Уменьшение ships_left.
    stats.ships_left -= 1
    # Обновление игровой информации.
     sb.prep_ships()
    # Очистка списков пришельцев и пуль.
    Сначала параметр sb добавляется в определение update_aliens()
    . Затем про- грамма передает sb функциям ship_hit()
     и check_aliens_bottom()
    , чтобы эти функции имели доступ к объекту
    Scoreboard
    .
    Затем определение ship_hit()
    изменяется с включением sb
    . Метод prep_ships()
    вызывается после уменьшения значения ships_left
    , так что при каждой потере корабля выводится правильное количество изображений.
    Вызов ship_hit()
    также включен в check_aliens_bottom()
    , так что эту функцию тоже нужно обновить:
    game_functions.py
    def check_aliens_bottom(ai_settings, screen, stats, sb, ship, aliens,
    bullets):
    """Проверяет, добрались ли пришельцы до нижнего края экрана."""

    306 Глава 14 • Ведение счета screen_rect = screen.get_rect()
    for alien in aliens.sprites():
    if alien.rect.bottom >= screen_rect.bottom:
    # Происходит то же, что при столкновении с кораблем.
    ship_hit(ai_settings, screen, stats, sb, ship, aliens, bullets)
    break
    Так как check_aliens_bottom()
    теперь получает параметр sb
    , мы добавляем аргу- мент sb в вызов ship_hit()
    Остается добавить sb в вызов update_aliens()
    в файле alien_invasion .py
    :
    alien_invasion.py
    # Запуск основного цикла игры.
    while True:
    if stats.game_active:
    ship.update()
    gf.update_bullets(ai_settings, screen, stats, sb, ship, aliens,
    bullets)
    gf.update_aliens(ai_settings, screen, stats, sb, ship, aliens,
    bullets)
    На рис. 14.6 показана полная игровая информация на экране, с количеством остав- шихся кораблей в левой верхней части экрана.
    Рис. 14.6. Полная игровая информация в Alien Invasion

    Итоги 307
    УПРАЖНЕНИЯ
    14-4 . Исторический рекорд: в текущей версии рекорд сбрасывается каждый раз, когда игрок закрывает и перезапускает Alien Invasion . Чтобы этого не происходило, запишите рекорд в файл перед вызовом sys .exit() и загрузите его при инициализации значения в GameStats .
    14-5 . Рефакторинг: найдите функции и методы, которые решают более одной задачи, и про- ведите рефакторинг, улучшающий структуру и эффективность кода . Например, переме- стите часть кода функции check_bullet_alien_collisions(), которая запускает новый уровень при уничтожении флота, в функцию start_new_level() . Также переместите четыре метода, вызываемых в методе __init__() класса Scoreboard, в метод prep_images() для сокращения длины __init__() . Метод prep_images() также может оказать помощь check_play_button() или start_game(), если вы уже провели рефакторинг check_play_button() .
    ПРИМЕЧАНИЕ
    Прежде чем браться за рефакторинг проекта, обратитесь к приложению Г . В нем расска- зано, как восстановить рабочее состояние проекта, если в ходе рефакторинга были до- пущены ошибки .
    14-6 . Расширение Alien Invasion: подумайте над возможными расширениями Alien Invasion .
    Например, пришельцы тоже могут стрелять по кораблю, или же вы можете добавить укры- тия, за которыми может скрываться корабль (укрытия могут разрушаться пулями с обеих сторон) . Или добавьте звуковые эффекты (например, взрывы или звуки выстрелов) сред- ствами модуля pygame .mixer .
    Итоги
    В этой главе вы узнали, как создать кнопку для запуска новой игры, как обнару- живать события мыши и скрывать указатель мыши в активных играх. Полученные знания помогут вам создать другие кнопки в играх, например кнопку для вывода инструкций по игре. Также вы научились изменять скорость по ходу игры, созда- вать прогрессивную систему подсчета очков и выводить информацию в текстовом и графическом виде.

    Проект 2
    Визуализация данных

    15
    Генерирование данных
    Под визуализацией данных понимается исследование данных через их визуальное представление. Визуализация тесно связана с анализом данных (data mining), ис- пользующим программный код для изучения закономерностей и связей в наборе данных. Набором данных может быть как маленький список чисел, помещающийся в одной строке кода, так и массивом из многих гигабайт.
    Качественное представление данных не сводится к красивой картинке. Если для набора данных подобрано простое, визуально привлекательное представление, его смысл становится очевидным для зрителя. Люди замечают в наборе данных закономерности, о которых они и не подозревали.
    К счастью, для визуализации сложных данных не нужен суперкомпьютер. Бла- годаря эффективности Python вы сможете быстро исследовать наборы данных из миллионов отдельных элементов данных (точек данных) на обычном ноутбуке.
    Элементы данных даже не обязаны быть числовыми. Приемы, о которых вы узнали в первой части книги, позволят вам проанализировать даже нечисловые данные.
    Python используется для обработки данных в генетике, исследовании климата, по- литическом и экономическом анализе и множестве других областей. Специалисты по обработке данных написали на Python впечатляющий инструментарий визуа- лизации и анализа, и многие из этих разработок также доступны и для вас. Один из самых популярных инструментов такого рода — matplotlib
    , математическая библиотека построения диаграмм. С помощью matplotlib можно строить простые диаграммы, графики, диаграммы разброса данных и т. д. После этого будет создан более интересный набор данных, основанный на концепции случайного блужда-
    ния — визуализации, генерируемой на базе серии случайных решений.
    Также в этом проекте будет использоваться пакет Pygal, ориентированный на создание визуализаций, хорошо работающих с цифровыми устройствами.
    С помощью Pygal можно выделять и изменять размеры элементов в ходе взаимо- действия пользователя с визуализацией; кроме того, размер визуализации легко изменяется под крошечные «умные часы» или гигантский монитор. Мы используем
    Pygal для исследования закономерностей различных бросков кубиков.
    Установка matplotlib
    Сначала необходимо установить библиотеку matplotlib
    , которая будет исполь- зоваться в исходном наборе визуализаций. Если вы еще не использовали про-

    310 Глава 15 • Генерирование данных грамму pip
    , обращайтесь к разделу «Установка пакетов Python с использованием pip» (с. 227).
    В Linux
    Если вы используете версию Python, входящую в поставку системы, вы сможете использовать менеджер пакетов своей системы для установки matplotlib всего одной командой:
    $ sudo apt-get install python3-matplotlib
    Если вы используете Python 2.7, команда выглядит так:
    $ sudo apt-get install python-matplotlib
    Если у вас установлена более новая версия Python, вам придется установить еще несколько библиотек, от которых зависит matplotlib
    :
    $ sudo apt-get install python3.5-dev python3.5-tk tk-dev
    $ sudo apt-get install libfreetype6-dev g++
    Затем программа pip используется для установки matplotlib
    :
    $ pip install --user matplotlib
    В OS X
    Компания Apple включает matplotlib в свою стандартную установку Python. Что- бы проверить, установлена ли библиотека в вашей системе, откройте терминальный сеанс и попробуйте импортировать matplotlib
    . Если библиотека matplotlib еще не установлена в системе и вы использовали Homebrew для установки Python, установите ее следующей командой:
    $ pip install --user matplotlib
    ПРИМЕЧАНИЕ
    Возможно, при установке пакетов вам придется использовать команду pip3 вместо pip . Если же эта команда не работает, попробуйте исключить флаг --user .
    В Windows
    В системе Windows сначала необходимо установить Visual Studio. Откройте стра- ницу https://dev.windows.com/, щелкните на ссылке
    Скачать средства
    (
    Downloads
    ) и найдите Visual Studio Community — бесплатный набор средств разработчика для
    Windows. Загрузите и запустите программу установки.
    Затем вам понадобится программа установки для matplotlib
    . Обратитесь по адресу https://pypi.python.org/pypi/matplotlib/ и найдите файл с расширени- ем
    .whl
    , соответствующий используемой версии Python. Например, если вы используете 32-разрядную версию Python 3.5, загрузите файл matplotlib-1 .4 .3- cp35-none-win32 .whl

    Построение простого графика 311
    ПРИМЕЧАНИЕ
    Если вы не нашли файл, соответствующий используемой версии Python, просмотрите возможные варианты по адресу http://www .lfd .uci .edu/

    gohlke/pythonlibs/#matplotlib . На этом сайте новые па- кеты появляются немного ранее, чем на официальном сайте matplotlib .
    Скопируйте файл
    .whl в каталог проекта, откройте окно командной строки и перейдите в каталог проекта. Используйте pip для установки matplotlib
    :
    > cd python_work
    python_work> python -m pip install --user matplotlib-1.4.3-cp35-none-win32.whl
    Тестирование matplotlib
    После того как необходимые пакеты будут установлены, протестируйте свою уста- новку. Для этого откройте сеанс командной строки командой python или python3
    и импортируйте matplotlib
    :
    $ python3
    >>> import matplotlib
    >>>
    Если на экране не появились сообщения об ошибках, значит, библиотека matplotlib установлена в вашей системе и вы можете переходить к следующему разделу.
    ПРИМЕЧАНИЕ
    Если у вас возникнут проблемы с установкой, поищите информацию в приложении В . Если ничего не помогает, обратитесь за помощью . Скорее всего, опытный программист Python быстро найдет причины возникших проблем с минимумом информации от вас .
    Галерея matplotlib
    Чтобы получить представления о визуализациях, которые можно строить в matplotlib
    , посетите галерею на сайте http://matplotlib.org/. Щелкая на визуали- зации в галерее, вы сможете просмотреть код, использованный для ее построения.
    Построение простого графика
    Начнем с построения простого линейного графика с использованием matplotlib
    , а затем настроим его для более содержательной визуализации данных. В качестве данных для графика будет использоваться последовательность квадратов 1, 4, 9,
    16 и 25.
    Передайте matplotlib числа так, как показано ниже, а matplotlib сделает все остальное:
    mpl_squares.py
    import matplotlib.pyplot as plt squares = [1, 4, 9, 16, 25]
    plt.plot(squares)
    plt.show()

    312 Глава 15 • Генерирование данных
    Сначала импортируйте модуль pyplot с псевдонимом plt
    , чтобы вам не приходи- лось многократно вводить имя pyplot
    . (Это сокращение часто встречается в приме- рах на сайте, поэтому мы поступим так же.) Модуль pyplot содержит ряд функций для построения диаграмм и графиков.
    Мы создаем список для хранения квадратов и передаем его функции plot()
    , ко- торая пытается построить осмысленное графическое представление для заданных чисел. Вызов plt.show()
    открывает окно просмотра matplotlib и выводит график
    (рис. 15.1). В окне просмотра можно изменять масштаб и перемещаться по по- строенному графику, а кнопка с диском позволяет сохранить любое изображение по вашему выбору.
    Рис. 15.1. Пример простейшего графика в matplotlib
    Изменение типа надписей и толщины графика
    Хотя из графика на рис. 15.1 видно, что числовая последовательность возрастает, текст надписей слишком мелкий, а линия слишком тонкая. К счастью, matplotlib позволяет настроить практически каждый аспект визуализации.
    Мы используем эти возможности настройки для того, чтобы сделать график более выразительным:
    mpl_squares.py
    import matplotlib.pyplot as plt squares = [1, 4, 9, 16, 25]
     plt.plot(squares, linewidth=5)
    # Назначение заголовка диаграммы и меток осей.
     plt.title("Square Numbers", fontsize=24)
     plt.xlabel("Value", fontsize=14)

    Построение простого графика 313
    plt.ylabel("Square of Value", fontsize=14)
    # Назначение размера шрифта делений на осях.
     plt.tick_params(axis='both', labelsize=14)
    plt.show()
    Параметр linewidth
     управляет толщиной линии, которая строится вызо- вом plot()
    . Функция title()
     назначает заголовок диаграммы. Параметры fontsize
    , неоднократно встречающиеся в коде, управляют размером текста диаграммы.
    Функции xlabel()
    и ylabel()
    позволяют назначить метки (заголовки) каж- дой из осей , а функция tick_params()
    определяет оформление делений на осях . Аргументы, использованные в данном примере, относятся к делениям на обоих осях (
    axes='both'
    ) и устанавливают для меток делений размер шрифта
    14 (
    labelsize=14
    ).
    Как видно из рис. 15.2, график выглядит гораздо лучше. Текст надписей стал круп- нее, а линия графика — толще.
    Рис. 15.2. График выглядит гораздо лучше
    Корректировка графика
    Теперь, когда текст на графике стал нормально читаться, мы видим, что данные помечены неправильно. Обратите внимание: для точки 4,0 в конце графика указан квадрат 25! Давайте исправим эту ошибку.
    Если plot()
    передает числовую последовательность, функция считает, что первый элемент данных соответствует координате x со значением 0, но в нашем примере первая точка соответствует значению 1. Чтобы переопределить значение по умол- чанию, передайте plot()
    как входные значения, так и квадраты:

    314 Глава 15 • Генерирование данных
    mpl_squares.py
    import matplotlib.pyplot as plt input_values = [1, 2, 3, 4, 5]
    squares = [1, 4, 9, 16, 25]
    plt.plot(input_values, squares, linewidth=5)
    # Назначение заголовка диаграммы и меток осей.
    Теперь plot()
    правильно строит график, потому что мы предоставили оба набора значений, и функции не нужно предполагать, как был сгенерирован выходной на- бор чисел. На рис. 15.3 изображен правильный график.
    1   ...   31   32   33   34   35   36   37   38   ...   53


    написать администратору сайта